├── .editorconfig ├── .eslintignore ├── .eslintrc.cjs ├── .git2gus └── config.json ├── .github ├── ISSUE_TEMPLATE │ ├── Bug_report.md │ └── Feature_request.md ├── PULL_REQUEST_TEMPLATE.md ├── dependabot.yml ├── no-response.yml └── workflows │ ├── automerge.yml │ ├── create-github-release.yml │ ├── devScripts.yml │ ├── failureNotifications.yml │ ├── notify-slack-on-pr-open.yml │ ├── onRelease.yml │ ├── test.yml │ └── validate-pr.yml ├── .gitignore ├── .husky ├── commit-msg ├── pre-commit └── pre-push ├── .images └── vscodeScreenshot.png ├── .lintstagedrc.cjs ├── .mocharc.json ├── .nycrc ├── .prettierrc.json ├── .sfdevrc.json ├── .vscode ├── launch.json ├── settings.json └── tasks.json ├── CHANGELOG.md ├── CODEOWNERS ├── CODE_OF_CONDUCT.md ├── CONTRIBUTING.md ├── DEVELOPING.md ├── LICENSE.txt ├── README.md ├── SECURITY.md ├── bin ├── dev.cmd ├── dev.js ├── run.cmd └── run.js ├── command-snapshot.json ├── commitlint.config.cjs ├── messages ├── package1_version_create.md ├── package1_version_create_get.md ├── package1_version_display.md ├── package1_version_list.md ├── package_convert.md ├── package_create.md ├── package_delete.md ├── package_displayancestry.md ├── package_install.md ├── package_install_report.md ├── package_installed_list.md ├── package_list.md ├── package_pushupgrade_abort.md ├── package_pushupgrade_list.md ├── package_pushupgrade_report.md ├── package_pushupgrade_schedule.md ├── package_uninstall.md ├── package_uninstall_report.md ├── package_update.md ├── package_version_create.md ├── package_version_create_list.md ├── package_version_create_report.md ├── package_version_delete.md ├── package_version_list.md ├── package_version_promote.md ├── package_version_report.md ├── package_version_retrieve.md ├── package_version_update.md └── packaging.md ├── package.json ├── schemas ├── package-convert.json ├── package-create.json ├── package-delete.json ├── package-install-report.json ├── package-install.json ├── package-installed-list.json ├── package-list.json ├── package-push__upgrade-abort.json ├── package-push__upgrade-list.json ├── package-push__upgrade-report.json ├── package-push__upgrade-schedule.json ├── package-uninstall-report.json ├── package-uninstall.json ├── package-update.json ├── package-version-create-list.json ├── package-version-create-report.json ├── package-version-create.json ├── package-version-delete.json ├── package-version-displayancestry.json ├── package-version-list.json ├── package-version-promote.json ├── package-version-report.json ├── package-version-retrieve.json ├── package-version-update.json ├── package1-version-create-get.json ├── package1-version-create.json ├── package1-version-display.json └── package1-version-list.json ├── src ├── commands │ ├── package │ │ ├── convert.ts │ │ ├── create.ts │ │ ├── delete.ts │ │ ├── install.ts │ │ ├── install │ │ │ └── report.ts │ │ ├── installed │ │ │ └── list.ts │ │ ├── list.ts │ │ ├── push-upgrade │ │ │ ├── abort.ts │ │ │ ├── list.ts │ │ │ ├── report.ts │ │ │ └── schedule.ts │ │ ├── uninstall.ts │ │ ├── uninstall │ │ │ └── report.ts │ │ ├── update.ts │ │ └── version │ │ │ ├── create.ts │ │ │ ├── create │ │ │ ├── list.ts │ │ │ └── report.ts │ │ │ ├── delete.ts │ │ │ ├── displayancestry.ts │ │ │ ├── list.ts │ │ │ ├── promote.ts │ │ │ ├── report.ts │ │ │ ├── retrieve.ts │ │ │ └── update.ts │ └── package1 │ │ └── version │ │ ├── create.ts │ │ ├── create │ │ └── get.ts │ │ ├── display.ts │ │ └── list.ts ├── index.ts └── utils │ ├── getProject.ts │ └── hubFlag.ts ├── test ├── .eslintrc.cjs ├── commands │ ├── package │ │ ├── install.nut.ts │ │ ├── install.test.ts │ │ ├── installReport.test.ts │ │ ├── packageConvert.test.ts │ │ ├── packageCreateAndDelete.nut.ts │ │ ├── packageInstalledList.nut.ts │ │ ├── packageList.nut.ts │ │ ├── packagePushUpgradeAbort.test.ts │ │ ├── packagePushUpgradeList.test.ts │ │ ├── packagePushUpgradeReport.test.ts │ │ ├── packagePushUpgradeSchedule.test.ts │ │ ├── packageUninstall.test.ts │ │ ├── packageVersion.nut.ts │ │ ├── packageVersionCreate.test.ts │ │ ├── packageVersionCreateReport.test.ts │ │ ├── packageVersionRetrieve.test.ts │ │ ├── version.delete.test.ts │ │ ├── versionPromoteUpdate.nut.ts │ │ └── versionReport.test.ts │ └── package1 │ │ ├── versionCreate.nut.ts │ │ ├── versionCreate.test.ts │ │ ├── versionCreateGet.test.ts │ │ ├── versionDisplay.nut.ts │ │ └── versionList.nut.ts └── tsconfig.json ├── tsconfig.json └── yarn.lock /.editorconfig: -------------------------------------------------------------------------------- 1 | root = true 2 | 3 | [*] 4 | indent_style = space 5 | indent_size = 2 6 | charset = utf-8 7 | trim_trailing_whitespace = true 8 | insert_final_newline = true 9 | 10 | [*.md] 11 | trim_trailing_whitespace = false 12 | -------------------------------------------------------------------------------- /.eslintignore: -------------------------------------------------------------------------------- 1 | *.cjs/ 2 | -------------------------------------------------------------------------------- /.eslintrc.cjs: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2021, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | module.exports = { 8 | extends: ['eslint-config-salesforce-typescript', 'eslint-config-salesforce-license', 'plugin:sf-plugin/recommended'], 9 | }; 10 | -------------------------------------------------------------------------------- /.git2gus/config.json: -------------------------------------------------------------------------------- 1 | { 2 | "productTag": "a1aB00000004Bx8IAE", 3 | "defaultBuild": "offcore.tooling.56", 4 | "issueTypeLabels": { 5 | "feature": "USER STORY", 6 | "regression": "BUG P1", 7 | "bug": "BUG P3" 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/Bug_report.md: -------------------------------------------------------------------------------- 1 | --- 2 | name: Bug report 3 | about: Create a report to help us improve 4 | --- 5 | 6 | 9 | 10 | 13 | 14 | ### Summary 15 | 16 | _Short summary of what is going on or to provide context_. 17 | 18 | ### Steps To Reproduce: 19 | 20 | 1. This is step 1. 21 | 1. This is step 2. All steps should start with '1.' 22 | 23 | ### Expected result 24 | 25 | _Describe what should have happened_. 26 | 27 | ### Actual result 28 | 29 | _Describe what actually happened instead_. 30 | 31 | ### Additional information 32 | 33 | _Feel free to attach a screenshot_. 34 | 35 | **VS Code Version**: 36 | 37 | **SF CLI Version**: 38 | 39 | **OS and version**: 40 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/Feature_request.md: -------------------------------------------------------------------------------- 1 | --- 2 | name: Feature request 3 | about: Suggest an idea for this project 4 | --- 5 | 6 | **Is your feature request related to a problem? Please describe.** 7 | A clear and concise description of what the problem is. Ex. I'm always frustrated when [...] 8 | 9 | **Describe the solution you'd like** 10 | A clear and concise description of what you want to happen. 11 | 12 | **Describe alternatives you've considered** 13 | A clear and concise description of any alternative solutions or features you've considered. 14 | 15 | **Additional context** 16 | Add any other context or screenshots about the feature request here. 17 | -------------------------------------------------------------------------------- /.github/PULL_REQUEST_TEMPLATE.md: -------------------------------------------------------------------------------- 1 | ### What does this PR do? 2 | 3 | ### What issues does this PR fix or reference? 4 | -------------------------------------------------------------------------------- /.github/dependabot.yml: -------------------------------------------------------------------------------- 1 | version: 2 2 | updates: 3 | - package-ecosystem: 'npm' 4 | directory: '/' 5 | schedule: 6 | interval: 'weekly' 7 | day: 'saturday' 8 | versioning-strategy: 'increase' 9 | labels: 10 | - 'dependencies' 11 | open-pull-requests-limit: 5 12 | pull-request-branch-name: 13 | separator: '-' 14 | commit-message: 15 | # cause a release for non-dev-deps 16 | prefix: fix(deps) 17 | # no release for dev-deps 18 | prefix-development: chore(dev-deps) 19 | ignore: 20 | - dependency-name: '@salesforce/dev-scripts' 21 | - dependency-name: '*' 22 | update-types: ['version-update:semver-major'] 23 | -------------------------------------------------------------------------------- /.github/no-response.yml: -------------------------------------------------------------------------------- 1 | # Configuration for probot-no-response - https://github.com/probot/no-response 2 | 3 | daysUntilClose: 7 4 | responseRequiredLabel: 'more information required' 5 | closeComment: > 6 | This issue has been automatically closed because there has been no response 7 | to our request for more information from the original author. Currently, there 8 | is not enough information provided for us to take action. Please reply and 9 | reopen this issue if you need additional assistance. 10 | -------------------------------------------------------------------------------- /.github/workflows/automerge.yml: -------------------------------------------------------------------------------- 1 | name: automerge 2 | on: 3 | workflow_dispatch: 4 | schedule: 5 | - cron: '42 2,5,8,11 * * *' 6 | 7 | jobs: 8 | automerge: 9 | uses: salesforcecli/github-workflows/.github/workflows/automerge.yml@main 10 | secrets: inherit 11 | -------------------------------------------------------------------------------- /.github/workflows/create-github-release.yml: -------------------------------------------------------------------------------- 1 | name: create-github-release 2 | 3 | on: 4 | push: 5 | branches: 6 | - main 7 | - prerelease/** 8 | tags-ignore: 9 | - '*' 10 | workflow_dispatch: 11 | inputs: 12 | prerelease: 13 | type: string 14 | description: 'Name to use for the prerelease: beta, dev, etc. NOTE: If this is already set in the package.json, it does not need to be passed in here.' 15 | 16 | jobs: 17 | release: 18 | uses: salesforcecli/github-workflows/.github/workflows/create-github-release.yml@main 19 | secrets: inherit 20 | with: 21 | prerelease: ${{ inputs.prerelease }} 22 | # If this is a push event, we want to skip the release if there are no semantic commits 23 | # However, if this is a manual release (workflow_dispatch), then we want to disable skip-on-empty 24 | # This helps recover from forgetting to add semantic commits ('fix:', 'feat:', etc.) 25 | skip-on-empty: ${{ github.event_name == 'push' }} 26 | -------------------------------------------------------------------------------- /.github/workflows/devScripts.yml: -------------------------------------------------------------------------------- 1 | name: devScripts 2 | on: 3 | workflow_dispatch: 4 | schedule: 5 | - cron: '50 6 * * 0' 6 | 7 | jobs: 8 | update: 9 | uses: salesforcecli/github-workflows/.github/workflows/devScriptsUpdate.yml@main 10 | secrets: inherit 11 | -------------------------------------------------------------------------------- /.github/workflows/failureNotifications.yml: -------------------------------------------------------------------------------- 1 | name: failureNotifications 2 | on: 3 | workflow_run: 4 | workflows: 5 | - publish 6 | types: 7 | - completed 8 | jobs: 9 | failure-notify: 10 | runs-on: ubuntu-latest 11 | if: ${{ github.event.workflow_run.conclusion == 'failure' }} 12 | steps: 13 | - name: Announce Failure 14 | id: slack 15 | uses: slackapi/slack-github-action@v1.26.0 16 | env: 17 | # for non-CLI-team-owned plugins, you can send this anywhere you like 18 | SLACK_WEBHOOK_URL: ${{ secrets.CLI_ALERTS_SLACK_WEBHOOK }} 19 | SLACK_WEBHOOK_TYPE: INCOMING_WEBHOOK 20 | with: 21 | # Payload can be visually tested here: https://app.slack.com/block-kit-builder/T01GST6QY0G#%7B%22blocks%22:%5B%5D%7D 22 | # Only copy over the "blocks" array to the Block Kit Builder 23 | payload: | 24 | { 25 | "text": "Workflow \"${{ github.event.workflow_run.name }}\" failed in ${{ github.event.workflow_run.repository.name }}", 26 | "blocks": [ 27 | { 28 | "type": "header", 29 | "text": { 30 | "type": "plain_text", 31 | "text": ":bh-alert: Workflow \"${{ github.event.workflow_run.name }}\" failed in ${{ github.event.workflow_run.repository.name }} :bh-alert:" 32 | } 33 | }, 34 | { 35 | "type": "section", 36 | "text": { 37 | "type": "mrkdwn", 38 | "text": "*Repo:* ${{ github.event.workflow_run.repository.html_url }}\n*Workflow name:* `${{ github.event.workflow_run.name }}`\n*Job url:* ${{ github.event.workflow_run.html_url }}" 39 | } 40 | } 41 | ] 42 | } 43 | -------------------------------------------------------------------------------- /.github/workflows/notify-slack-on-pr-open.yml: -------------------------------------------------------------------------------- 1 | name: Pull Request Slack Notification 2 | 3 | on: 4 | pull_request: 5 | types: [opened, reopened] 6 | 7 | jobs: 8 | build: 9 | runs-on: ubuntu-latest 10 | steps: 11 | - name: Notify Slack on PR open 12 | env: 13 | WEBHOOK_URL : ${{ secrets.CLI_TEAM_SLACK_WEBHOOK_URL }} 14 | PULL_REQUEST_AUTHOR_ICON_URL : ${{ github.event.pull_request.user.avatar_url }} 15 | PULL_REQUEST_AUTHOR_NAME : ${{ github.event.pull_request.user.login }} 16 | PULL_REQUEST_AUTHOR_PROFILE_URL: ${{ github.event.pull_request.user.html_url }} 17 | PULL_REQUEST_BASE_BRANCH_NAME : ${{ github.event.pull_request.base.ref }} 18 | PULL_REQUEST_COMPARE_BRANCH_NAME : ${{ github.event.pull_request.head.ref }} 19 | PULL_REQUEST_NUMBER : ${{ github.event.pull_request.number }} 20 | PULL_REQUEST_REPO: ${{ github.event.pull_request.head.repo.name }} 21 | PULL_REQUEST_TITLE : ${{ github.event.pull_request.title }} 22 | PULL_REQUEST_URL : ${{ github.event.pull_request.html_url }} 23 | uses: salesforcecli/github-workflows/.github/actions/prNotification@main 24 | -------------------------------------------------------------------------------- /.github/workflows/onRelease.yml: -------------------------------------------------------------------------------- 1 | name: publish 2 | 3 | on: 4 | release: 5 | types: [published] 6 | # support manual release in case something goes wrong and needs to be repeated or tested 7 | workflow_dispatch: 8 | inputs: 9 | tag: 10 | description: tag that needs to publish 11 | type: string 12 | required: true 13 | jobs: 14 | # parses the package.json version and detects prerelease tag (ex: beta from 4.4.4-beta.0) 15 | getDistTag: 16 | outputs: 17 | tag: ${{ steps.distTag.outputs.tag }} 18 | runs-on: ubuntu-latest 19 | steps: 20 | - uses: actions/checkout@v4 21 | with: 22 | ref: ${{ github.event.release.tag_name || inputs.tag }} 23 | - uses: salesforcecli/github-workflows/.github/actions/getPreReleaseTag@main 24 | id: distTag 25 | npm: 26 | uses: salesforcecli/github-workflows/.github/workflows/npmPublish.yml@main 27 | needs: [getDistTag] 28 | with: 29 | ctc: true 30 | sign: true 31 | tag: ${{ needs.getDistTag.outputs.tag || 'latest' }} 32 | githubTag: ${{ github.event.release.tag_name || inputs.tag }} 33 | secrets: inherit 34 | -------------------------------------------------------------------------------- /.github/workflows/test.yml: -------------------------------------------------------------------------------- 1 | name: tests 2 | on: 3 | push: 4 | branches-ignore: [main] 5 | workflow_dispatch: 6 | 7 | env: 8 | ONEGP_TESTKIT_AUTH_URL: ${{secrets.ONEGP_TESTKIT_AUTH_URL}} 9 | 10 | jobs: 11 | yarn-lockfile-check: 12 | uses: salesforcecli/github-workflows/.github/workflows/lockFileCheck.yml@main 13 | # Since the Windows unit tests take much longer, we run the linux unit tests first and then run the windows unit tests in parallel with NUTs 14 | linux-unit-tests: 15 | needs: yarn-lockfile-check 16 | uses: salesforcecli/github-workflows/.github/workflows/unitTestsLinux.yml@main 17 | windows-unit-tests: 18 | needs: linux-unit-tests 19 | uses: salesforcecli/github-workflows/.github/workflows/unitTestsWindows.yml@main 20 | nuts: 21 | needs: linux-unit-tests 22 | uses: salesforcecli/github-workflows/.github/workflows/nut.yml@main 23 | secrets: inherit 24 | strategy: 25 | matrix: 26 | os: [ubuntu-latest, windows-latest] 27 | command: 28 | - 'yarn test:nuts:package' 29 | # - 'yarn test:nuts:package1' disable because of the long-standing ORA bug 30 | fail-fast: false 31 | with: 32 | os: ${{ matrix.os }} 33 | command: ${{ matrix.command }} 34 | -------------------------------------------------------------------------------- /.github/workflows/validate-pr.yml: -------------------------------------------------------------------------------- 1 | name: pr-validation 2 | 3 | on: 4 | pull_request: 5 | types: [opened, reopened, edited] 6 | # only applies to PRs that want to merge to main 7 | branches: [main] 8 | 9 | jobs: 10 | pr-validation: 11 | uses: salesforcecli/github-workflows/.github/workflows/validatePR.yml@main 12 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # -- CLEAN 2 | tmp/ 3 | # use yarn by default, so ignore npm 4 | package-lock.json 5 | 6 | # never checkin npm config 7 | .npmrc 8 | 9 | # debug logs 10 | npm-error.log 11 | yarn-error.log 12 | 13 | 14 | # compile source 15 | lib 16 | 17 | # test artifacts 18 | *xunit.xml 19 | *checkstyle.xml 20 | *unitcoverage 21 | .nyc_output 22 | coverage 23 | test_session* 24 | 25 | # generated docs 26 | docs 27 | 28 | # ignore sfdx-trust files 29 | *.tgz 30 | *.sig 31 | package.json.bak. 32 | 33 | 34 | npm-shrinkwrap.json 35 | oclif.manifest.json 36 | oclif.lock 37 | 38 | # -- CLEAN ALL 39 | *.tsbuildinfo 40 | .eslintcache 41 | .wireit 42 | node_modules 43 | 44 | # -- 45 | # put files here you don't want cleaned with sf-clean 46 | 47 | # os specific files 48 | .DS_Store 49 | .idea 50 | .iml 51 | plugin-packaging.iml 52 | .codegenie 53 | -------------------------------------------------------------------------------- /.husky/commit-msg: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | . "$(dirname "$0")/_/husky.sh" 3 | 4 | yarn commitlint --edit 5 | -------------------------------------------------------------------------------- /.husky/pre-commit: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | . "$(dirname "$0")/_/husky.sh" 3 | 4 | yarn lint && yarn pretty-quick --staged 5 | -------------------------------------------------------------------------------- /.husky/pre-push: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | . "$(dirname "$0")/_/husky.sh" 3 | 4 | yarn build && yarn test 5 | -------------------------------------------------------------------------------- /.images/vscodeScreenshot.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/salesforcecli/plugin-packaging/eaf1228bf437f7d66b05e12678223288e9657edc/.images/vscodeScreenshot.png -------------------------------------------------------------------------------- /.lintstagedrc.cjs: -------------------------------------------------------------------------------- 1 | module.exports = { 2 | '**/*.{js,json,md}?(x)': () => 'npm run reformat', 3 | }; 4 | -------------------------------------------------------------------------------- /.mocharc.json: -------------------------------------------------------------------------------- 1 | { 2 | "require": ["ts-node/register"], 3 | "watch-extensions": "ts", 4 | "recursive": true, 5 | "reporter": "spec", 6 | "timeout": 20000, 7 | "node-option": ["loader=ts-node/esm"] 8 | } 9 | -------------------------------------------------------------------------------- /.nycrc: -------------------------------------------------------------------------------- 1 | { 2 | "nyc": { 3 | "extends": "@salesforce/dev-config/nyc" 4 | } 5 | } -------------------------------------------------------------------------------- /.prettierrc.json: -------------------------------------------------------------------------------- 1 | "@salesforce/prettier-config" 2 | -------------------------------------------------------------------------------- /.sfdevrc.json: -------------------------------------------------------------------------------- 1 | { 2 | "exclude-scripts": ["docs"] 3 | } 4 | -------------------------------------------------------------------------------- /.vscode/launch.json: -------------------------------------------------------------------------------- 1 | { 2 | // Use IntelliSense to learn about possible attributes. 3 | // Hover to view descriptions of existing attributes. 4 | // For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387 5 | "version": "0.2.0", 6 | "configurations": [ 7 | { 8 | "type": "node", 9 | "request": "attach", 10 | "name": "Attach", 11 | "port": 9229, 12 | "skipFiles": ["/**"] 13 | }, 14 | { 15 | "name": "Run All Tests", 16 | "type": "node", 17 | "request": "launch", 18 | "protocol": "inspector", 19 | "program": "${workspaceFolder}/node_modules/mocha/bin/_mocha", 20 | "args": ["--inspect", "--no-timeouts", "--colors", "test/**/*.test.ts"], 21 | "env": { 22 | "NODE_ENV": "development", 23 | "SFDX_ENV": "development" 24 | }, 25 | "sourceMaps": true, 26 | "smartStep": true, 27 | "internalConsoleOptions": "openOnSessionStart", 28 | "preLaunchTask": "Compile" 29 | }, 30 | { 31 | "type": "node", 32 | "request": "launch", 33 | "name": "Run Current Test", 34 | "program": "${workspaceFolder}/node_modules/mocha/bin/_mocha", 35 | "args": ["--inspect", "--no-timeouts", "--colors", "${file}"], 36 | "env": { 37 | "NODE_ENV": "development", 38 | "SFDX_ENV": "development" 39 | }, 40 | "sourceMaps": true, 41 | "smartStep": true, 42 | "internalConsoleOptions": "openOnSessionStart", 43 | "preLaunchTask": "Compile" 44 | } 45 | ] 46 | } 47 | -------------------------------------------------------------------------------- /.vscode/settings.json: -------------------------------------------------------------------------------- 1 | { 2 | "files.exclude": { 3 | "**/.git": true, 4 | "**/.svn": true, 5 | "**/.hg": true, 6 | "**/CVS": true, 7 | "**/.DS_Store": true 8 | }, 9 | "search.exclude": { 10 | "**/lib": true, 11 | "**/bin": true 12 | }, 13 | "editor.tabSize": 2, 14 | "editor.formatOnSave": true, 15 | "rewrap.wrappingColumn": 80 16 | } 17 | -------------------------------------------------------------------------------- /.vscode/tasks.json: -------------------------------------------------------------------------------- 1 | { 2 | "version": "2.0.0", 3 | "problemMatcher": "$tsc-watch", 4 | "tasks": [ 5 | { 6 | "label": "Compile", 7 | "group": { 8 | "kind": "build", 9 | "isDefault": true 10 | }, 11 | "command": "yarn", 12 | "type": "shell", 13 | "presentation": { 14 | "focus": false, 15 | "panel": "dedicated" 16 | }, 17 | "args": ["run", "prepack"], 18 | "isBackground": false, 19 | "problemMatcher": { 20 | "owner": "typescript", 21 | "fileLocation": "relative", 22 | "pattern": { 23 | "regexp": "^(.*\\.ts):(\\d*):(\\d*)(\\s*-\\s*)(error|warning|info)\\s*(TS\\d*):\\s*(.*)$", 24 | "file": 1, 25 | "line": 2, 26 | "column": 3, 27 | "severity": 5, 28 | "code": 6, 29 | "message": 7 30 | } 31 | } 32 | }, 33 | { 34 | "label": "Lint", 35 | "command": "yarn", 36 | "type": "shell", 37 | "presentation": { 38 | "focus": false, 39 | "panel": "dedicated" 40 | }, 41 | "args": ["run", "lint"], 42 | "isBackground": false, 43 | "problemMatcher": { 44 | "owner": "typescript", 45 | "fileLocation": "relative", 46 | "pattern": { 47 | "regexp": "^(ERROR|WARNING|INFO):\\s*(.*\\.ts):(\\d*):(\\d*)(\\s*-\\s*)(.*)$", 48 | "file": 2, 49 | "line": 3, 50 | "column": 4, 51 | "severity": 1, 52 | "message": 6 53 | } 54 | } 55 | } 56 | ] 57 | } 58 | -------------------------------------------------------------------------------- /CODEOWNERS: -------------------------------------------------------------------------------- 1 | # Techical writers will be added as reviewers on markdown changes. 2 | *.md @salesforcecli/cli-docs 3 | 4 | # Comment line immediately above ownership line is reserved for related other information. Please be careful while editing. 5 | #ECCN:Open Source 5D002 -------------------------------------------------------------------------------- /CONTRIBUTING.md: -------------------------------------------------------------------------------- 1 | ## Contributing 2 | 3 | 1. The [DEVELOPING](DEVELOPING.md) doc has details on how to set up your environment. 4 | 1. Create a new issue before starting your project so that we can keep track of 5 | what you are trying to add/fix. That way, we can also offer suggestions or 6 | let you know if there is already an effort in progress. 7 | 1. Fork this repository (external contributors) or branch off main (committers). 8 | 1. Create a _topic_ branch in your fork based on the main branch. Note, this step is recommended but technically not required if contributing using a fork. 9 | 1. Edit the code in your fork/branch. 10 | 1. Write appropriate tests for your changes. Try to achieve at least 95% code coverage on any new code. No pull request will be accepted without associated tests. 11 | 1. Sign CLA (see [CLA](#cla) below). 12 | 1. Send us a pull request when you are done. We'll review your code, suggest any 13 | needed changes, and merge it in. 14 | 1. Upon merge, a new release of the `@salesforce/plugin-packaging` plugin will be published to npmjs with a version bump corresponding to commitizen rules. 15 | 16 | ### CLA 17 | 18 | External contributors will be required to sign a Contributor's License 19 | Agreement. You can do so by going to https://cla.salesforce.com/sign-cla. 20 | 21 | ## Branches 22 | 23 | - We work in branches off of `main`. 24 | - Our released (aka. _production_) branch is `main`. 25 | - Our work happens in _topic_ branches (feature and/or bug-fix). 26 | - feature as well as bug-fix branches are based on `main` 27 | - branches _should_ be kept up-to-date using `rebase` 28 | - [commit messages are enforced](DEVELOPING.md#When-you-are-ready-to-commit) 29 | 30 | ## Pull Requests 31 | 32 | - Develop features and bug fixes in _topic_ branches off main, or forks. 33 | - _Topic_ branches can live in forks (external contributors) or within this repository (committers). 34 | \*\* When creating _topic_ branches in this repository please prefix with `/`. 35 | - PRs will be reviewed and merged by committers. 36 | 37 | ## Releasing 38 | 39 | - A new version of this plugin (`@salesforce/plugin-packaging`) will be published upon merging PRs to `main`, with the version number increment based on commitizen rules. 40 | -------------------------------------------------------------------------------- /SECURITY.md: -------------------------------------------------------------------------------- 1 | ## Security 2 | 3 | Please report any security issue to [security@salesforce.com](mailto:security@salesforce.com) 4 | as soon as it is discovered. This library limits its runtime dependencies in 5 | order to reduce the total cost of ownership as much as can be, but all consumers 6 | should remain vigilant and have their security stakeholders review all third-party 7 | products (3PP) like this one and their dependencies. 8 | -------------------------------------------------------------------------------- /bin/dev.cmd: -------------------------------------------------------------------------------- 1 | @echo off 2 | 3 | node --loader ts-node/esm --no-warnings=ExperimentalWarning "%~dp0\dev" %* 4 | -------------------------------------------------------------------------------- /bin/dev.js: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env -S node --loader ts-node/esm --no-warnings=ExperimentalWarning 2 | // eslint-disable-next-line node/shebang 3 | async function main() { 4 | const { execute } = await import('@oclif/core'); 5 | await execute({ development: true, dir: import.meta.url }); 6 | } 7 | 8 | await main(); 9 | -------------------------------------------------------------------------------- /bin/run.cmd: -------------------------------------------------------------------------------- 1 | @echo off 2 | 3 | node "%~dp0\run" %* -------------------------------------------------------------------------------- /bin/run.js: -------------------------------------------------------------------------------- 1 | #!/usr/bin/env node 2 | 3 | // eslint-disable-next-line node/shebang 4 | async function main() { 5 | const { execute } = await import('@oclif/core'); 6 | await execute({ dir: import.meta.url }); 7 | } 8 | 9 | await main(); 10 | -------------------------------------------------------------------------------- /commitlint.config.cjs: -------------------------------------------------------------------------------- 1 | module.exports = { extends: ['@commitlint/config-conventional'] }; 2 | -------------------------------------------------------------------------------- /messages/package1_version_create.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | Create a first-generation package version in the release org. 4 | 5 | # description 6 | 7 | The package version is based on the contents of the specified metadata package. Omit --managed-released if you want to create an unmanaged package version. 8 | 9 | # examples 10 | 11 | - Create a first-generation package version from the package with the specified ID and name the package version "example"; use your default org: 12 | 13 | <%= config.bin %> <%= command.id %> --package-id 033... --name example 14 | 15 | - Same as previous example, but provide a description and wait for 30 minutes for the package version to be created; use the specified org: 16 | 17 | <%= config.bin %> <%= command.id %> --package-id 033... --name example --description "example description" --wait 30 --target-org myorg@example.com 18 | 19 | # flags.package-id.summary 20 | 21 | ID of the metadata package (starts with 033) of which you’re creating a new version. 22 | 23 | # flags.name.summary 24 | 25 | Package version name. 26 | 27 | # flags.description.summary 28 | 29 | Package version description. 30 | 31 | # flags.version.summary 32 | 33 | Package version in major.minor format, for example, 3.2. 34 | 35 | # flags.release-notes-url.summary 36 | 37 | Release notes URL. 38 | 39 | # flags.release-notes-url.description 40 | 41 | This link is displayed in the package installation UI to provide release notes for this package version to subscribers. 42 | 43 | # flags.post-install-url.summary 44 | 45 | Post install URL. 46 | 47 | # flags.post-install-url.description 48 | 49 | The contents of the post-installation instructions URL are displayed in the UI after installation of the package version. 50 | 51 | # flags.managed-released.summary 52 | 53 | Create a managed package version. 54 | 55 | # flags.managed-released.description 56 | 57 | To create a beta version, don’t include this parameter. 58 | 59 | # flags.installation-key.summary 60 | 61 | Installation key for key-protected package (default: null). 62 | 63 | # flags.wait.summary 64 | 65 | Minutes to wait for the package version to be created (default: 2 minutes). 66 | 67 | # uploadFailure 68 | 69 | Package upload failed. ${os.EOL}%s 70 | 71 | # package1VersionCreateCommandInvalidVersion 72 | 73 | Version supplied, %s, is not formatted correctly. Enter in major.minor format, for example, 3.2. 74 | 75 | # SUCCESS 76 | 77 | Successfully uploaded package [%s] 78 | 79 | # QUEUED 80 | 81 | PackageUploadRequest has been enqueued. You can query the status using 82 | %s package1:version:create:get -i %s -o %s 83 | -------------------------------------------------------------------------------- /messages/package1_version_create_get.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | Retrieve the status of a package version creation request. 4 | 5 | # examples 6 | 7 | - Get the status of the creation request for the package version with the specified ID in your default org: 8 | 9 | <%= config.bin %> <%= command.id %> --request-id 0HD... 10 | 11 | - Same as previous example, but use the specified org: 12 | 13 | <%= config.bin %> <%= command.id %> --request-id 0HD... --target-org myorg@example.com 14 | 15 | # flags.request-id.summary 16 | 17 | ID of the PackageUploadRequest (starts with 0HD). 18 | 19 | # IN_PROGRESS 20 | 21 | PackageUploadRequest is still InProgress. You can query the status using 22 | %s package1:version:create:get -i %s -o %s 23 | 24 | # SUCCESS 25 | 26 | Successfully uploaded package [%s] 27 | 28 | # QUEUED 29 | 30 | PackageUploadRequest has been enqueued. You can query the status using 31 | %s package1:version:create:get -i %s -o %s 32 | 33 | # uploadFailure 34 | 35 | Package upload failed. 36 | %s 37 | -------------------------------------------------------------------------------- /messages/package1_version_display.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | Display details about a first-generation package version. 4 | 5 | # flags.package-version-id.summary 6 | 7 | ID (starts with 04t) of the metadata package version whose details you want to display. 8 | 9 | # examples 10 | 11 | - Display details about the first-generation package version with the specified ID in your default org: 12 | 13 | <%= config.bin %> <%= command.id %> --package-version-id 04t... 14 | 15 | - Same as previous example, but use the specified org: 16 | 17 | <%= config.bin %> <%= command.id %> --package-version-id 04t... --target-org myorg@example.com 18 | -------------------------------------------------------------------------------- /messages/package1_version_list.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | List package versions for the specified first-generation package or for the org. 4 | 5 | # flags.package-id.summary 6 | 7 | Metadata package ID (starts with 033) whose package versions you want to list. 8 | 9 | # flags.package-id.description 10 | 11 | If not specified, shows all versions for all packages (managed and unmanaged) in the org. 12 | 13 | # examples 14 | 15 | - List all first-generation package versions in your default org: 16 | 17 | <%= config.bin %> <%= command.id %> 18 | 19 | - List package versions for the specified first-generation package in the specifief org: 20 | 21 | <%= config.bin %> <%= command.id %> --package-id 033... --target-org myorg@example.com 22 | -------------------------------------------------------------------------------- /messages/package_convert.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | Create a second-generation package version from a first-generation package. 4 | 5 | # description 6 | 7 | The package convert creates a new package in the Dev Hub if one does not already exist for the specified first-generation package. 8 | 9 | It then creates a new package version in the Dev Hub with contents based on the specified first-generation package. 10 | 11 | By default, the latest released non-patch version from the specified first-generation package will be converted. Use --patch-version to override the default. Read more about --patch-version option in help 12 | 13 | To retrieve details about a package version create request, including status and package version ID (04t), run "<%= config.bin %> package version create report -i 08c...". 14 | 15 | We recommend specifying the --installation-key to protect the contents of your package and to prevent unauthorized installation of your package. 16 | 17 | To list package version creation requests in the org, run "<%= config.bin %> package version create list". 18 | 19 | # examples 20 | 21 | - Create a second-generation package version from the first-generation package with the specified ID and give it the installation key "password123"; uses your default Dev Hub org: 22 | 23 | <%= config.bin %> <%= command.id %> --package 033... --installation-key password123 24 | 25 | - Similar to previous example, but uses the specified Dev Hub org: 26 | 27 | <%= config.bin %> <%= command.id %> --package 033... --installation-key password123 --target-dev-hub devhuborg@example.com 28 | 29 | # flags.package.summary 30 | 31 | ID (starts with 033) of the first-generation package to convert. 32 | 33 | # flags.installation-key.summary 34 | 35 | Installation key for key-protected package. 36 | 37 | # flags.installation-key.description 38 | 39 | Either an --installation-key value or the --installation-key-bypass flag is required. 40 | 41 | # flags.installation-key-bypass.summary 42 | 43 | Bypass the installation key requirement. 44 | 45 | # flags.installation-key-bypass.description 46 | 47 | If you bypass this requirement, anyone can install your package. Either an --installation-key value or the --installation-key-bypass flag is required. 48 | 49 | # flags.definition-file.summary 50 | 51 | Path to a definition file that contains features and org preferences that the metadata of the package version depends on. 52 | 53 | # flags.definition-file.description 54 | 55 | This definition file is similar to the scratch org definition file. 56 | 57 | # flags.wait.summary 58 | 59 | Minutes to wait for the package version to be created. 60 | 61 | # flags.build-instance.summary 62 | 63 | Instance where the conversion package version will be created, such as NA50. 64 | 65 | # flags.verbose.summary 66 | 67 | Display verbose command output. 68 | 69 | # in-progress 70 | 71 | Request in progress. Will wait a total of %s more seconds before timing out. Current Status='%s' 72 | 73 | # flags.seed-metadata.summary 74 | 75 | Directory containing metadata to be deployed prior to conversion. 76 | 77 | # flags.seed-metadata.description 78 | 79 | The directory containing metadata that will be deployed on the build org prior to attempting conversion. 80 | 81 | # flags.patch-version.summary 82 | 83 | Specific released patch version to convert 84 | 85 | # flags.patch-version.description 86 | 87 | Specify a released patch version as major.minor.patch.build to convert to second generation package version 88 | -------------------------------------------------------------------------------- /messages/package_create.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | Create a package. 4 | 5 | # description 6 | 7 | First, use this command to create a package. Then create a package version. 8 | 9 | If you don’t have a namespace defined in your sfdx-project.json file, use --no-namespace. 10 | 11 | Your --name value must be unique within your namespace. 12 | 13 | Run '<%= config.bin %> package list to list all packages in the Dev Hub org. 14 | 15 | # examples 16 | 17 | - Create an unlocked package from the files in the "force-app" directory; uses your default Dev Hub org: 18 | 19 | <%= config.bin %> <%= command.id %> --name MyUnlockedPackage --package-type Unlocked --path force-app 20 | 21 | - Create a managed packaged from the "force-app" directory files, give the package a description, and use the specified Dev Hub org: 22 | 23 | <%= config.bin %> <%= command.id %> --name MyManagedPackage --description "Your Package Descripton" --package-type Managed --path force-app --target-dev-hub devhub@example.com 24 | 25 | # flags.name.summary 26 | 27 | Name of the package to create. 28 | 29 | # flags.org-dependent.summary 30 | 31 | Depends on unpackaged metadata in the installation org; applies to unlocked packages only. 32 | 33 | # flags.org-dependent.description 34 | 35 | Use Source Tracking in Sandboxes to develop your org-dependent unlocked package. For more information, see "Create Org-Dependent Unlocked Packages" in the Salesforce DX Developer Guide. 36 | 37 | # flags.error-notification-username.summary 38 | 39 | Active Dev Hub user designated to receive email notifications for package errors. 40 | 41 | # flags.error-notification-username.description 42 | 43 | Email notifications include information about unhandled Apex exceptions, and install, upgrade, or uninstall failures associated with your package. 44 | 45 | # flags.description.summary 46 | 47 | Description of the package. 48 | 49 | # flags.no-namespace.summary 50 | 51 | Create the package with no namespace; available only for unlocked packages. 52 | 53 | # flags.no-namespace.description 54 | 55 | This flag is useful when you’re migrating an existing org to packages. But use a namespaced package for new metadata. 56 | 57 | # flags.package-type.summary 58 | 59 | Type of package. 60 | 61 | # flags.package-type.description 62 | 63 | The options for package type are Managed and Unlocked (Managed=DeveloperManagedSubscriberManaged, Unlocked=DeveloperControlledSubscriberEditable). These options determine upgrade and editability rules. 64 | 65 | # flags.path.summary 66 | 67 | Path to directory that contains the contents of the package. 68 | -------------------------------------------------------------------------------- /messages/package_delete.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | Delete a package. 4 | 5 | # description 6 | 7 | Specify the ID or alias of the package you want to delete. 8 | 9 | Delete unlocked and second-generation managed packages. Before you delete a package, first delete all associated package versions. 10 | 11 | # examples 12 | 13 | - Delete a package using its alias from your default Dev Hub org: 14 | 15 | <%= config.bin %> <%= command.id %> --package "Your Package Alias" 16 | 17 | - Delete a package using its ID from the specified Dev Hub org: 18 | 19 | <%= config.bin %> <%= command.id %> --package 0Ho... --target-dev-hub devhub@example.com 20 | 21 | # flags.package.summary 22 | 23 | ID (starts with 0Ho) or alias of the package to delete. 24 | 25 | # flags.undelete.summary 26 | 27 | Undelete a deleted package. 28 | 29 | # flags.no-prompt.summary 30 | 31 | Don’t prompt before deleting the package. 32 | 33 | # prompt-delete 34 | 35 | Deleted packages can’t be recovered. 36 | 37 | Do you want to continue? (y/n) 38 | 39 | # prompt-undelete 40 | 41 | This will undelete the package, which may result in unintended consequences for customers. Proceed with caution. 42 | 43 | Do you want to continue? (y/n) 44 | 45 | # prompt-delete-deny 46 | 47 | The request to delete this package was canceled 48 | 49 | # humanSuccess 50 | 51 | Successfully deleted the package with ID: %s 52 | 53 | # humanSuccessUndelete 54 | 55 | Successfully undeleted the package. 56 | -------------------------------------------------------------------------------- /messages/package_displayancestry.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | Display the ancestry tree for a 2GP managed package version. 4 | 5 | # examples 6 | 7 | - Display the ancestry tree for a package version with the specified alias, using your default Dev Hub org: 8 | 9 | <%= config.bin %> <%= command.id %> --package package_version_alias 10 | 11 | - Similar to previous example, but display the output in DOT code: 12 | 13 | <%= config.bin %> <%= command.id %> --package package_version_alias --dot-code 14 | 15 | - Display the ancestry tree for a package with the specified ID, using the Dev Hub org with username devhub@example.com: 16 | 17 | <%= config.bin %> <%= command.id %> --package OHo... --target-dev-hub devhub@example.com 18 | 19 | - Display the ancestry tree of a package version with the specified ID, using your default Dev Hub org: 20 | 21 | <%= config.bin %> <%= command.id %> --package 04t... 22 | 23 | # flags.package.summary 24 | 25 | ID or alias of the package (starts with 0Ho) or package version (starts with 04t) to display ancestry for. 26 | 27 | # flags.package.description 28 | 29 | If you specify a package ID (starts with 0Ho) or alias, the ancestor tree for every package version associated with the package ID is displayed. If you specify a package version (starts with 04t) or alias, the ancestry tree of the specified package version is displayed. 30 | 31 | # flags.dot-code.summary 32 | 33 | Display the ancestry tree in DOT code. 34 | 35 | # flags.dot-code.description 36 | 37 | You can use the DOT code output in graph visualization software to create tree visualizations. 38 | 39 | # flags.verbose.summary 40 | 41 | Display both the package version ID (starts with 04t) and the version number (major.minor.patch.build) in the ancestry tree. 42 | -------------------------------------------------------------------------------- /messages/package_install_report.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | Retrieve the status of a package installation request. 4 | 5 | # examples 6 | 7 | - Retrieve the status of a package installation request with the specified ID on your default org: 8 | 9 | <%= config.bin %> <%= command.id %> --request-id 0Hf... 10 | 11 | - Similar to previous example, except use the org with username me@example.com: 12 | 13 | <%= config.bin %> <%= command.id %> --request-id 0Hf... --target-org me@example.com 14 | 15 | # flags.request-id.summary 16 | 17 | ID of the package install request you want to check; starts with 0Hf. 18 | -------------------------------------------------------------------------------- /messages/package_installed_list.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | List the org’s installed packages. 4 | 5 | # examples 6 | 7 | - List the installed packages in your default org: 8 | 9 | <%= config.bin %> <%= command.id %> 10 | 11 | - List the installed packages in the org with username me@example.com: 12 | 13 | <%= config.bin %> <%= command.id %> --target-org me@example.com 14 | -------------------------------------------------------------------------------- /messages/package_list.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | List all packages in the Dev Hub org. 4 | 5 | # description 6 | 7 | You can view the namespace, IDs, and other details for each package. 8 | 9 | # examples 10 | 11 | - List all packages in the specified Dev Hub org: 12 | 13 | <%= config.bin %> <%= command.id %> --target-dev-hub devhub@example.com 14 | 15 | - List all packages details in the specified Dev Hub org, and show extended details about each package: 16 | 17 | <%= config.bin %> <%= command.id %> --target-dev-hub devhub@example.com --verbose 18 | 19 | # namespace 20 | 21 | Namespace Prefix 22 | 23 | # name 24 | 25 | Name 26 | 27 | # id 28 | 29 | Id 30 | 31 | # package-id 32 | 33 | Subscriber Package Id 34 | 35 | # alias 36 | 37 | Alias 38 | 39 | # description 40 | 41 | Description 42 | 43 | # package-type 44 | 45 | Type 46 | 47 | # flags.verbose.summary 48 | 49 | Display extended package detail. 50 | 51 | # convertedFromPackageId 52 | 53 | Converted From Package Id 54 | 55 | # isOrgDependent 56 | 57 | Org-Dependent Unlocked Package 58 | 59 | # error-notification-username 60 | 61 | Error Notification Username 62 | 63 | # createdBy 64 | 65 | Created By 66 | 67 | # app-analytics-enabled 68 | 69 | App Analytics Enabled -------------------------------------------------------------------------------- /messages/package_pushupgrade_abort.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | Abort a package push upgrade that has been scheduled. Only push upgrade requests with a status of Created or Pending can be aborted. 4 | 5 | # description 6 | 7 | Specify the request ID for which you want abort the request. If applicable, the command displays errors related to the request. 8 | 9 | To show all requests in the org, run "<%= config.bin %> package pushupgrade list --package 033...". 10 | 11 | # examples 12 | 13 | - Cancel the specified package push upgrade request with the specified ID; uses your default Dev Hub org: 14 | 15 | <%= config.bin %> <%= command.id %> --push-request-id 0DV... 16 | 17 | - Cancel the specified package push upgrade request in the Dev Hub org with username devhub@example.com: 18 | 19 | <%= config.bin %> <%= command.id %> --push-request-id 0DV... --target-dev-hub devhub@example.com 20 | 21 | # flags.push-request-id.summary 22 | 23 | ID of the package push request (starts with 0DV). This ID is returned after the package push-upgrade schedule command completes successfully. 24 | 25 | # flags.target-dev-hub.summary 26 | 27 | Username or alias of the Dev Hub org. 28 | 29 | # flags.target-dev-hub.description 30 | 31 | Overrides the value of the target-dev-hub configuration variable, if set. 32 | 33 | # error.invalid-push-request-id-owner 34 | 35 | Can’t abort package push upgrade request. The specified push upgrade ID is associated with a package in a different Dev Hub org. Retry this command in the context of the Dev Hub org that owns the package. 36 | 37 | # error.invalid-push-request-id 38 | 39 | Can’t abort package push upgrade request. The specified push upgrade ID isn’t valid. Check the ID (starts with 0DV) and retry the command. 40 | 41 | # error.invalid-push-request-status 42 | 43 | Can’t abort package push upgrade request with status '${pushRequest.Status}'. Only push upgrade requests with a status of 'Created' or 'Pending' can be cancelled. 44 | 45 | # status 46 | 47 | Status 48 | 49 | # output 50 | 51 | Scheduled push upgrade ID [%s] was cancelled. 52 | -------------------------------------------------------------------------------- /messages/package_pushupgrade_list.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | Lists the status of push upgrade requests for a given package. 4 | 5 | # description 6 | 7 | Shows the details of each request to create a push upgrade in the Dev Hub org. 8 | 9 | All filter parameters are applied using the AND logical operator (not OR). 10 | 11 | To get information about a specific request, run "sf package pushupgrade report" and supply the request ID. 12 | 13 | # flags.package.summary 14 | 15 | Package ID (starts with 033) of the package that you want push upgrade information for. 16 | 17 | # flags.scheduled-last-days.summary 18 | 19 | Number of days in the past for which to display the list of push upgrade requests that were scheduled. Used to filter the list output to only recently scheduled push upgrades. 20 | 21 | # flags.status.summary 22 | 23 | Status used to filter the list output Valid values are: Created, Canceled, Pending, In Progress, Failed, or Succeeded 24 | 25 | # flags.show-push-migrations-only.summary 26 | 27 | Display only push upgrade requests for package migrations. 28 | 29 | # examples 30 | 31 | - List all package push upgrade requests in the specified Dev Hub org: 32 | 33 | <%= config.bin %> <%= command.id %> --package 033xyz --target-dev-hub myHub 34 | 35 | - List all package push upgrade requests in the specified Dev Hub org scheduled in the last 30 days: 36 | 37 | <%= config.bin %> <%= command.id %> --package 033xyz --scheduled-last-days 30 --target-dev-hub myHub 38 | 39 | - List all package push upgrade with a status Succeeded: 40 | 41 | <%= config.bin %> <%= command.id %> --package 033xyz –-status Succeeded 42 | 43 | - List all package push upgrade with a status Failed: 44 | 45 | <%= config.bin %> <%= command.id %> --package 033xyz –-status Failed 46 | 47 | # id 48 | 49 | ID 50 | 51 | # status 52 | 53 | Status 54 | 55 | # package-id 56 | 57 | Package Id 58 | 59 | # packageVersionId 60 | 61 | Package Version Id 62 | -------------------------------------------------------------------------------- /messages/package_pushupgrade_report.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | Retrieve the status of a package push upgrade. 4 | 5 | # description 6 | 7 | Specify the request ID for which you want to view details. If applicable, the command displays errors related to the request. 8 | 9 | To show all requests in the org, run "<%= config.bin %> package pushupgrade list". 10 | 11 | # examples 12 | 13 | - Retrieve details about the package push upgrade with the specified ID; uses your default Dev Hub org: 14 | 15 | <%= config.bin %> <%= command.id %> --push-request-id 0DV... 16 | 17 | - Retrieve details about the specified package push request in the Dev Hub org with username devhub@example.com: 18 | 19 | <%= config.bin %> <%= command.id %> --push-request-id 0DV... --target-dev-hub devhub@example.com 20 | 21 | # flags.push-request-id.summary 22 | 23 | ID of the package push request (starts with 0DV). This ID is returned after the package push-upgrade schedule command completes successfully. 24 | 25 | # truncatedErrors 26 | 27 | To see all errors, run: %s data query -q "SELECT ErrorMessage FROM PackagePushError WHERE PackagePushJob.PackagePushRequestId='%s'" 28 | -------------------------------------------------------------------------------- /messages/package_uninstall.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | Uninstall a second-generation package from the target org. 4 | 5 | # description 6 | 7 | Specify the package ID for a second-generation package. 8 | 9 | To list the org’s installed packages, run "<%= config.bin %> package installed list". 10 | 11 | To uninstall a first-generation package, from Setup, enter Installed Packages in the Quick Find box, then select Installed Packages. 12 | 13 | # examples 14 | 15 | - Uninstall a package with specified ID from an org with username me@example.com: 16 | 17 | <%= config.bin %> <%= command.id %> --package 04t... --target-org me@example.com 18 | 19 | - Uninstall a package with the specified alias from your default org: 20 | 21 | <%= config.bin %> <%= command.id %> --package undesirable_package_alias 22 | 23 | - Uninstall a package with an alias that contains spaces from your default org: 24 | 25 | <%= config.bin %> <%= command.id %> --package "Undesirable Package Alias" 26 | 27 | # flags.wait.summary 28 | 29 | Number of minutes to wait for uninstall status. 30 | 31 | # flags.package.summary 32 | 33 | ID (starts with 04t) or alias of the package version to uninstall. 34 | 35 | # InProgress 36 | 37 | PackageUninstallRequest is currently InProgress. 38 | You can continue to query the status using %s package uninstall report -i %s -o %s 39 | 40 | # Success 41 | 42 | Successfully uninstalled package [%s] 43 | -------------------------------------------------------------------------------- /messages/package_uninstall_report.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | Retrieve the status of a package uninstall request. 4 | 5 | # examples 6 | 7 | - Retrieve the status of a package uninstall in your default org using the specified request ID: 8 | 9 | <%= config.bin %> <%= command.id %> --request-id 06y... 10 | 11 | - Similar to previous example, but use the org with username me@example.com: 12 | 13 | <%= config.bin %> <%= command.id %> --request-id 06y... --target-org me@example.com 14 | 15 | # flags.request-id.summary 16 | 17 | ID of the package uninstall request you want to check; starts with 06y. 18 | 19 | # InProgress 20 | 21 | PackageUninstallRequest is currently InProgress. You can continue to query the status using 22 | %s package:uninstall:report -i %s -o %s 23 | 24 | # Unknown 25 | 26 | TODO: fix me 27 | 28 | # Success 29 | 30 | Successfully uninstalled package [%s] 31 | 32 | # package-id-invalid 33 | 34 | Verify that you entered a valid package uninstall request ID (starts with 06y) and try again. 35 | -------------------------------------------------------------------------------- /messages/package_update.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | Update package details. 4 | 5 | # description 6 | 7 | Specify a new value for each option you want to update. 8 | 9 | Run "<%= config.bin %> package list" to list all packages in the Dev Hub org. 10 | 11 | # examples 12 | 13 | - Update the name of the package with the specified alias; uses your default Dev Hub org: 14 | 15 | <%= config.bin %> <%= command.id %> --package "Your Package Alias" --name "New Package Name" 16 | 17 | - Update the description of the package with the specified ID; uses the specified Dev Hub org: 18 | 19 | <%= config.bin %> <%= command.id %> --package 0Ho... --description "New Package Description" --target-dev-hub devhub@example.com 20 | 21 | # flags.package.summary 22 | 23 | ID (starts with 0Ho) or alias of the package to update. 24 | 25 | # flags.name.summary 26 | 27 | New name of the package. 28 | 29 | # flags.description.summary 30 | 31 | New description of the package. 32 | 33 | # flags.enable-app-analytics.summary 34 | 35 | Enable AppExchange App Analytics usage data collection on this managed package and its components. 36 | 37 | # success 38 | 39 | Successfully updated the package. %s 40 | -------------------------------------------------------------------------------- /messages/package_version_create_list.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | List package version creation requests. 4 | 5 | # description 6 | 7 | Shows the details of each request to create a package version in the Dev Hub org. 8 | 9 | All filter parameters are applied using the AND logical operator (not OR). 10 | 11 | To get information about a specific request, run "<%= config.bin %> package version create report" and supply the request ID. 12 | 13 | # flags.status.summary 14 | 15 | Status of the version creation request, used to filter the list. 16 | 17 | # flags.show-conversions-only.summary 18 | 19 | Filter the list output to display only converted package version. 20 | 21 | # flags.verbose.summary 22 | 23 | Displays additional information at a slight performance cost, such as the version name and number for each package version create request. 24 | 25 | # examples 26 | 27 | - List all package version creation requests in your default Dev Hub org: 28 | 29 | <%= config.bin %> <%= command.id %> 30 | 31 | - List package version creation requests from the last 3 days in the Dev Hub org with username devhub@example.com: 32 | 33 | <%= config.bin %> <%= command.id %> --created-last-days 3 --target-dev-hub 34 | 35 | - List package version creation requests with status Error: 36 | 37 | <%= config.bin %> <%= command.id %> --status Error 38 | 39 | - List package version creation requests with status InProgress: 40 | 41 | <%= config.bin %> <%= command.id %> --status InProgress 42 | 43 | - List package version creation requests with status Success that were created today: 44 | 45 | <%= config.bin %> <%= command.id %> --created-last-days 0 --status Success 46 | 47 | # id 48 | 49 | ID 50 | 51 | # status 52 | 53 | Status 54 | 55 | # package-id 56 | 57 | Package Id 58 | 59 | # packageVersionId 60 | 61 | Package Version Id 62 | 63 | # subscriberPackageVersionId 64 | 65 | Subscriber Package Version Id 66 | 67 | # branch 68 | 69 | Branch 70 | 71 | # tag 72 | 73 | Tag 74 | 75 | # installUrl 76 | 77 | Installation URL 78 | 79 | # createdBy 80 | 81 | Created By 82 | 83 | # convertedFromVersionId 84 | 85 | Converted From Version Id 86 | -------------------------------------------------------------------------------- /messages/package_version_create_report.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | Retrieve details about a package version creation request. 4 | 5 | # description 6 | 7 | Specify the request ID for which you want to view details. If applicable, the command displays errors related to the request. 8 | 9 | To show all requests in the org, run "<%= config.bin %> package version create list". 10 | 11 | # examples 12 | 13 | - Retrieve details about the package version creation request with the specified ID; uses your default Dev Hub org: 14 | 15 | <%= config.bin %> <%= command.id %> --package-create-request-id 08c... 16 | 17 | - Retrieve details about the specified package version creation request in the Dev Hub org with username devhub@example.com: 18 | 19 | <%= config.bin %> <%= command.id %> --package-create-request-id 08c... --target-dev-hub devhub@example.com 20 | 21 | # flags.package-create-request-id.summary 22 | 23 | ID (starts with 08c) of the package version creation request you want to display. 24 | 25 | # truncatedErrors 26 | 27 | ... 28 | 29 | To see all errors, run: %s data query -t -q "SELECT Message FROM Package2VersionCreateRequestError WHERE ParentRequest.Id='%s'" -o %s 30 | -------------------------------------------------------------------------------- /messages/package_version_delete.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | Delete a package version. 4 | 5 | # description 6 | 7 | Specify the ID or alias of the package version you want to delete. In second-generation managed packaging, only beta package versions can be deleted. Before deleting a package version, review the considerations outlined in https://developer.salesforce.com/docs/atlas.en-us.pkg2_dev.meta/pkg2_dev/sfdx_dev_dev2gp_package_deletion.htm. 8 | 9 | # examples 10 | 11 | - Delete a package version with the specified alias using your default Dev Hub org: 12 | 13 | <%= config.bin %> <%= command.id %> --package "Your Package Alias" 14 | 15 | - Delete a package version with the specified ID using the Dev Hub org with username "devhub@example.com": 16 | 17 | <%= config.bin %> <%= command.id %> --package 04t... --target-org devhub@example.com 18 | 19 | # flags.package.summary 20 | 21 | ID (starts with 04t) or alias of the package version to delete. 22 | 23 | # flags.undelete.summary 24 | 25 | Undelete a deleted package version. 26 | 27 | # flags.no-prompt.summary 28 | 29 | Don’t prompt before deleting the package version. 30 | 31 | # prompt-delete 32 | 33 | Deleted package versions can’t be recovered. 34 | 35 | Do you want to continue? (y/n) 36 | 37 | # prompt-undelete 38 | 39 | This will undelete the package version, which may result in unintended consequences for customers. Proceed with caution. 40 | 41 | Do you want to continue? (y/n) 42 | 43 | # prompt-delete-deny 44 | 45 | The request to delete this package version has been canceled. 46 | 47 | # humanSuccess 48 | 49 | Successfully deleted the package version with ID: %s 50 | 51 | # humanSuccessUndelete 52 | 53 | Successfully undeleted package version %s. 54 | -------------------------------------------------------------------------------- /messages/package_version_list.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | List all package versions in the Dev Hub org. 4 | 5 | # description 6 | 7 | The command displays details of each package version in the org. Use --concise or --verbose to display limited or additional details, respectively. 8 | 9 | All filter parameters are applied using the AND logical operator (not OR). 10 | 11 | # flags.concise.summary 12 | 13 | Display limited package version details. 14 | 15 | # flags.branch.summary 16 | 17 | Branch in your source control system used to filter the results; only package versions based on the specified branch are listed. 18 | 19 | # flags.packages.summary 20 | 21 | Comma-delimited list of packages (aliases or 0Ho IDs) to list. 22 | 23 | # flags.released.summary 24 | 25 | Display released versions only (IsReleased=true). 26 | 27 | # flags.order-by.summary 28 | 29 | Package version fields used to order the list. 30 | 31 | # flags.verbose.summary 32 | 33 | Display extended package version details. 34 | 35 | # flags.show-conversions-only.summary 36 | 37 | Filter the list output to display only converted package version. 38 | 39 | # examples 40 | 41 | - List package versions in your default Dev Hub org that were created in the last 3 days; show only the released versions and order the list using the PatchVersion field. Display extended details about each package version: 42 | 43 | <%= config.bin %> <%= command.id %> --verbose --created-last-days 3 --released --order-by PatchVersion 44 | 45 | - List the released package versions for the two specified packages that were modified today; use the Dev Hub org with username devhub@example.com: 46 | 47 | <%= config.bin %> <%= command.id %> --packages 0Ho000000000000,0Ho000000000001 --released --modified-last-days 0 --target-dev-hub devhub@example.com 48 | 49 | - List all released package versions in your default Dev Hub org: 50 | 51 | <%= config.bin %> <%= command.id %> --released 52 | 53 | - List package versions that were modified today in your default Dev Hub org; show limited details about each one: 54 | 55 | <%= config.bin %> <%= command.id %> --concise --modified-last-days 0 56 | 57 | - List package versions that are based on the "featureA" branch in your source control system that were modified today in your default Dev Hub org; show limited details about each one: 58 | 59 | <%= config.bin %> <%= command.id %> --concise --modified-last-days 0 --branch featureA 60 | 61 | - List released package versions that were created in the last 3 days in your default Dev Hub org; show limited details: 62 | 63 | <%= config.bin %> <%= command.id %> --concise --created-last-days 3 --released 64 | 65 | - List released package versions that were modified today for the two packages with specified aliases in your default Dev Hub org: 66 | 67 | <%= config.bin %> <%= command.id %> --packages exp-mgr,exp-mgr-util --released --modified-last-days 0 68 | 69 | # name 70 | 71 | Name 72 | 73 | # description 74 | 75 | Description 76 | 77 | # version 78 | 79 | Version 80 | 81 | # id 82 | 83 | Package Version Id 84 | 85 | # alias 86 | 87 | Alias 88 | 89 | # subscriberPackageVersionId 90 | 91 | Subscriber Package Version Id 92 | 93 | # convertedFromVersionId 94 | 95 | Converted From Version Id 96 | 97 | # package-id 98 | 99 | Package Id 100 | 101 | # packageBranch 102 | 103 | Branch 104 | 105 | # packageTag 106 | 107 | Tag 108 | 109 | # installUrl 110 | 111 | Installation URL 112 | 113 | # installKey 114 | 115 | Installation Key 116 | 117 | # codeCoverage 118 | 119 | Code Coverage 120 | 121 | # hasPassedCodeCoverageCheck 122 | 123 | Code Coverage Met 124 | 125 | # validationSkipped 126 | 127 | Validation Skipped 128 | 129 | # validatedAsync 130 | 131 | Validated Async 132 | 133 | # releaseVersion 134 | 135 | Release Version 136 | 137 | # buildDurationInSeconds 138 | 139 | Build Duration in Seconds 140 | 141 | # hasMetadataRemoved 142 | 143 | Managed Metadata Removed 144 | 145 | # isOrgDependent 146 | 147 | Org-Dependent Unlocked Package 148 | 149 | # createdBy 150 | 151 | Created By 152 | 153 | # language 154 | 155 | Language 156 | 157 | # endToEndBuildDurationInSeconds 158 | 159 | End To End Build Duration In Seconds 160 | -------------------------------------------------------------------------------- /messages/package_version_promote.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | Promote a package version to released. 4 | 5 | # description 6 | 7 | Supply the ID or alias of the package version you want to promote. Promotes the package version to released status. 8 | 9 | # examples 10 | 11 | - Promote the package version with the specified ID to released; uses your default Dev Hub org: 12 | 13 | <%= config.bin %> <%= command.id %> --package 04t... 14 | 15 | - Promote the package version with the specified alias to released; uses the Dev Hub org with username devhub@example.com: 16 | 17 | <%= config.bin %> <%= command.id %> --package awesome_package_alias --target-dev-hub devhub@example.com 18 | 19 | - Promote the package version with an alias that has spaces to released: 20 | 21 | <%= config.bin %> <%= command.id %> --package "Awesome Package Alias" 22 | 23 | # flags.package.summary 24 | 25 | ID (starts with 04t) or alias of the package version to promote. 26 | 27 | # packageVersionPromoteConfirm 28 | 29 | Are you sure you want to release package version %s? You can't undo this action. Release package (y/n)? 30 | 31 | # promote-deny 32 | 33 | Promote operation denied 34 | 35 | # flags.no-prompt.summary 36 | 37 | Don't prompt to confirm setting the package version as released. 38 | 39 | # humanSuccess 40 | 41 | Successfully promoted the package version, ID: %s, to released. 42 | 43 | # previouslyReleasedMessage 44 | 45 | You already promoted a package version with this major.minor.patch version number. For a given major.minor.patch number, you can promote only one version. 46 | 47 | # previouslyReleasedAction 48 | 49 | Create a new package version with a different --version-number, then promote the package version. 50 | %s package:version:create -p -n -k 51 | %s package:version:promote -p 05ixxx 52 | 53 | # hasMetadataRemovedWarning 54 | 55 | The package version you've created doesn't contain metadata components that were in the package version's ancestor. 56 | -------------------------------------------------------------------------------- /messages/package_version_report.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | Retrieve details about a package version in the Dev Hub org. 4 | 5 | # description 6 | 7 | To update package version values, run "<%= config.bin %> package version update". 8 | 9 | # examples 10 | 11 | - Retrieve details about the package version with the specified ID from your default Dev Hub org: 12 | 13 | <%= config.bin %> <%= command.id %> --package 04t... 14 | 15 | - Retrieve details about the package version with the specified alias (that contains spaces) from the Dev Hub org with username devhub@example.com: 16 | 17 | <%= config.bin %> <%= command.id %> --package "Your Package Alias" --target-dev-hub devhub@example.com 18 | 19 | # flags.package.summary 20 | 21 | ID (starts with 04t) or alias of the package to retrieve details for. 22 | 23 | # flags.verbose.summary 24 | 25 | Display extended package version details. 26 | 27 | # dependencies 28 | 29 | Dependencies 30 | 31 | # codeCoveragePercentages 32 | 33 | Code Coverage Details 34 | 35 | # ancestorId 36 | 37 | Ancestor 38 | 39 | # ancestorVersion 40 | 41 | Ancestor Version 42 | 43 | # isReleased 44 | 45 | Released 46 | -------------------------------------------------------------------------------- /messages/package_version_retrieve.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | Retrieve package metadata for a specified package version. 4 | 5 | # description 6 | 7 | Retrieving a package version downloads the metadata into the directory you specify. 8 | 9 | You can retrieve metadata for a second- or first-generation managed package, or an unlocked package. 10 | 11 | Specify the subscriber package version ID (starts with 04t) and the path to an empty directory when you run this command. 12 | 13 | # examples 14 | 15 | - Retrieve package metadata for a subscriber package version ID (starts with 04t) into my-folder/ within your Salesforce DX project directory: 16 | 17 | <%= config.bin %> <%= command.id %> --package 04t... --output-dir my-folder –-target-org my-scratch 18 | 19 | If you omit --target-org, this command runs against your default org. 20 | 21 | # flags.package.summary 22 | 23 | Subscriber package version ID (starts with 04t). 24 | 25 | # flags.output-dir.summary 26 | 27 | Path within your Salesforce DX project directory in which to download the metadata. This directory must be empty. 28 | 29 | # headers.fullName 30 | 31 | FULL NAME 32 | 33 | # headers.type 34 | 35 | TYPE 36 | 37 | # headers.filePath 38 | 39 | PROJECT PATH 40 | 41 | # error.failedToDownloadZip 42 | 43 | Can’t retrieve package version metadata. Ensure that you've specified the correct 04t ID for the package version and then retry this command. 44 | -------------------------------------------------------------------------------- /messages/package_version_update.md: -------------------------------------------------------------------------------- 1 | # summary 2 | 3 | Update a package version. 4 | 5 | # description 6 | 7 | Specify a new value for each option you want to update. 8 | 9 | To display details about a package version, run "<%= config.bin %> package version display". 10 | 11 | # examples 12 | 13 | - Update the package version that has the specified alias (that contains spaces) with a new installation key "password123"; uses your default Dev Hub org: 14 | 15 | <%= config.bin %> <%= command.id %> --package "Your Package Alias" --installation-key password123 16 | 17 | - Update the package version that has the specified ID with a new branch and tag; use the Dev Hub org with username devhub@example.com: 18 | 19 | <%= config.bin %> <%= command.id %> --package 04t... --branch main --tag 'Release 1.0.7' --target-dev-hub devhub@example.com 20 | 21 | - Update the package version that has the specified ID with a new description: 22 | 23 | <%= config.bin %> <%= command.id %> --package 04t... --version-description "New Package Version Description" 24 | 25 | # flags.package.summary 26 | 27 | ID (starts with 04t) or alias of the package to update a version of. 28 | 29 | # flags.version-name.summary 30 | 31 | New package version name. 32 | 33 | # flags.version-description.summary 34 | 35 | New package version description. 36 | 37 | # flags.branch.summary 38 | 39 | New package version branch. 40 | 41 | # flags.tag.summary 42 | 43 | New package version tag. 44 | 45 | # flags.installation-key.summary 46 | 47 | New installation key for key-protected package (default: null) 48 | 49 | # success 50 | 51 | Successfully updated the package version. %s 52 | -------------------------------------------------------------------------------- /messages/packaging.md: -------------------------------------------------------------------------------- 1 | # flags.created-last-days.summary 2 | 3 | Number of days since the request was created, starting at 00:00:00 of first day to now. Use 0 for today. 4 | 5 | # flags.modified-last-days.summary 6 | 7 | Number of days since the items were modified, starting at 00:00:00 of first day to now. Use 0 for today. 8 | -------------------------------------------------------------------------------- /schemas/package-convert.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/PackageVersionCreateRequestResult", 4 | "definitions": { 5 | "PackageVersionCreateRequestResult": { 6 | "type": "object", 7 | "properties": { 8 | "Id": { 9 | "type": "string" 10 | }, 11 | "Status": { 12 | "$ref": "#/definitions/PackagingSObjects.Package2VersionStatus" 13 | }, 14 | "Package2Id": { 15 | "type": "string" 16 | }, 17 | "Package2Name": { 18 | "type": ["string", "null"] 19 | }, 20 | "Package2VersionId": { 21 | "type": "string" 22 | }, 23 | "SubscriberPackageVersionId": { 24 | "type": ["string", "null"] 25 | }, 26 | "Tag": { 27 | "type": "string" 28 | }, 29 | "Branch": { 30 | "type": "string" 31 | }, 32 | "Error": { 33 | "type": "array", 34 | "items": {} 35 | }, 36 | "CreatedDate": { 37 | "type": "string" 38 | }, 39 | "HasMetadataRemoved": { 40 | "type": ["boolean", "null"] 41 | }, 42 | "HasPassedCodeCoverageCheck": { 43 | "type": ["boolean", "null"] 44 | }, 45 | "CodeCoverage": { 46 | "type": ["number", "null"] 47 | }, 48 | "VersionNumber": { 49 | "type": ["string", "null"] 50 | }, 51 | "CreatedBy": { 52 | "type": "string" 53 | }, 54 | "ConvertedFromVersionId": { 55 | "type": ["string", "null"] 56 | }, 57 | "TotalNumberOfMetadataFiles": { 58 | "type": ["number", "null"] 59 | }, 60 | "TotalSizeOfMetadataFiles": { 61 | "type": ["number", "null"] 62 | } 63 | }, 64 | "required": [ 65 | "Id", 66 | "Status", 67 | "Package2Id", 68 | "Package2Name", 69 | "Package2VersionId", 70 | "SubscriberPackageVersionId", 71 | "Tag", 72 | "Branch", 73 | "Error", 74 | "CreatedDate", 75 | "HasMetadataRemoved", 76 | "HasPassedCodeCoverageCheck", 77 | "CodeCoverage", 78 | "VersionNumber", 79 | "CreatedBy", 80 | "ConvertedFromVersionId", 81 | "TotalNumberOfMetadataFiles", 82 | "TotalSizeOfMetadataFiles" 83 | ], 84 | "additionalProperties": false 85 | }, 86 | "PackagingSObjects.Package2VersionStatus": { 87 | "type": "string", 88 | "enum": [ 89 | "Queued", 90 | "InProgress", 91 | "Success", 92 | "Error", 93 | "Initializing", 94 | "VerifyingFeaturesAndSettings", 95 | "VerifyingDependencies", 96 | "VerifyingMetadata", 97 | "FinalizingPackageVersion", 98 | "PerformingValidations" 99 | ] 100 | } 101 | } 102 | } 103 | -------------------------------------------------------------------------------- /schemas/package-create.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/PackageCreate", 4 | "definitions": { 5 | "PackageCreate": { 6 | "type": "object", 7 | "properties": { 8 | "Id": { 9 | "type": "string" 10 | } 11 | }, 12 | "required": ["Id"], 13 | "additionalProperties": false 14 | } 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /schemas/package-delete.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/PackageSaveResult", 4 | "definitions": { 5 | "PackageSaveResult": { 6 | "$ref": "#/definitions/SaveResult" 7 | }, 8 | "SaveResult": { 9 | "anyOf": [ 10 | { 11 | "type": "object", 12 | "properties": { 13 | "success": { 14 | "type": "boolean", 15 | "const": true 16 | }, 17 | "id": { 18 | "type": "string" 19 | }, 20 | "errors": { 21 | "type": "array", 22 | "items": { 23 | "not": {} 24 | } 25 | } 26 | }, 27 | "required": ["success", "id", "errors"], 28 | "additionalProperties": false 29 | }, 30 | { 31 | "type": "object", 32 | "properties": { 33 | "success": { 34 | "type": "boolean", 35 | "const": false 36 | }, 37 | "id": { 38 | "not": {} 39 | }, 40 | "errors": { 41 | "type": "array", 42 | "items": { 43 | "$ref": "#/definitions/SaveError" 44 | } 45 | } 46 | }, 47 | "required": ["success", "errors"], 48 | "additionalProperties": false 49 | } 50 | ] 51 | }, 52 | "SaveError": { 53 | "type": "object", 54 | "properties": { 55 | "errorCode": { 56 | "type": "string" 57 | }, 58 | "message": { 59 | "type": "string" 60 | }, 61 | "fields": { 62 | "type": "array", 63 | "items": { 64 | "type": "string" 65 | } 66 | } 67 | }, 68 | "required": ["errorCode", "message"], 69 | "additionalProperties": false 70 | } 71 | } 72 | } 73 | -------------------------------------------------------------------------------- /schemas/package-installed-list.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/PackageInstalledCommandResult", 4 | "definitions": { 5 | "PackageInstalledCommandResult": { 6 | "type": "array", 7 | "items": { 8 | "$ref": "#/definitions/PackageInstalledListResult" 9 | } 10 | }, 11 | "PackageInstalledListResult": { 12 | "type": "object", 13 | "properties": { 14 | "Id": { 15 | "type": "string" 16 | }, 17 | "SubscriberPackageId": { 18 | "type": "string" 19 | }, 20 | "SubscriberPackageName": { 21 | "type": "string" 22 | }, 23 | "SubscriberPackageNamespace": { 24 | "type": "string" 25 | }, 26 | "SubscriberPackageVersionId": { 27 | "type": "string" 28 | }, 29 | "SubscriberPackageVersionName": { 30 | "type": "string" 31 | }, 32 | "SubscriberPackageVersionNumber": { 33 | "type": "string" 34 | } 35 | }, 36 | "required": ["Id"], 37 | "additionalProperties": false 38 | } 39 | } 40 | } 41 | -------------------------------------------------------------------------------- /schemas/package-list.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/PackageListCommandResult", 4 | "definitions": { 5 | "PackageListCommandResult": { 6 | "type": "array", 7 | "items": { 8 | "$ref": "#/definitions/Package2Result" 9 | } 10 | }, 11 | "Package2Result": { 12 | "type": "object", 13 | "additionalProperties": false, 14 | "properties": { 15 | "SubscriberPackageId": { 16 | "type": "string" 17 | }, 18 | "Description": { 19 | "type": "string" 20 | }, 21 | "NamespacePrefix": { 22 | "type": "string" 23 | }, 24 | "ContainerOptions": { 25 | "$ref": "#/definitions/PackageType" 26 | }, 27 | "ConvertedFromPackageId": { 28 | "type": "string" 29 | }, 30 | "PackageErrorUsername": { 31 | "type": "string" 32 | }, 33 | "AppAnalyticsEnabled": { 34 | "type": "boolean" 35 | }, 36 | "Alias": { 37 | "type": "string" 38 | }, 39 | "CreatedBy": { 40 | "type": "string" 41 | }, 42 | "IsOrgDependent": { 43 | "type": "string" 44 | }, 45 | "Id": { 46 | "type": "string" 47 | }, 48 | "Name": { 49 | "type": "string" 50 | } 51 | } 52 | }, 53 | "PackageType": { 54 | "type": "string", 55 | "enum": ["Managed", "Unlocked"] 56 | } 57 | } 58 | } 59 | -------------------------------------------------------------------------------- /schemas/package-push__upgrade-abort.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/PackagePushUpgradeAbortResult", 4 | "definitions": { 5 | "PackagePushUpgradeAbortResult": { 6 | "type": "object", 7 | "properties": { 8 | "success": { 9 | "type": "boolean" 10 | } 11 | }, 12 | "required": [ 13 | "success" 14 | ], 15 | "additionalProperties": false 16 | } 17 | } 18 | } -------------------------------------------------------------------------------- /schemas/package-push__upgrade-list.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/PackagePushRequestListResultArr", 4 | "definitions": { 5 | "PackagePushRequestListResultArr": { 6 | "type": "array", 7 | "items": { 8 | "$ref": "#/definitions/PackagePushRequestListResult" 9 | } 10 | }, 11 | "PackagePushRequestListResult": { 12 | "type": "object", 13 | "properties": { 14 | "Id": { 15 | "type": "string" 16 | }, 17 | "PackageVersionId": { 18 | "type": "string" 19 | }, 20 | "PackageVersion": { 21 | "type": "object", 22 | "properties": { 23 | "Name": { 24 | "type": "string" 25 | }, 26 | "MajorVersion": { 27 | "type": "string" 28 | }, 29 | "MinorVersion": { 30 | "type": "string" 31 | } 32 | }, 33 | "required": [ 34 | "Name", 35 | "MajorVersion", 36 | "MinorVersion" 37 | ], 38 | "additionalProperties": false 39 | }, 40 | "Status": { 41 | "type": "string" 42 | }, 43 | "ScheduledStartTime": { 44 | "type": "string" 45 | }, 46 | "StartTime": { 47 | "type": "string" 48 | }, 49 | "EndTime": { 50 | "type": "string" 51 | }, 52 | "OrgsScheduled": { 53 | "type": "number" 54 | }, 55 | "OrgsUpgradeSucceeded": { 56 | "type": "number" 57 | }, 58 | "OrgsUpgradeFailed": { 59 | "type": "number" 60 | } 61 | }, 62 | "required": [ 63 | "Id", 64 | "PackageVersionId", 65 | "PackageVersion", 66 | "Status", 67 | "ScheduledStartTime", 68 | "StartTime", 69 | "EndTime", 70 | "OrgsScheduled", 71 | "OrgsUpgradeSucceeded", 72 | "OrgsUpgradeFailed" 73 | ], 74 | "additionalProperties": false 75 | } 76 | } 77 | } -------------------------------------------------------------------------------- /schemas/package-push__upgrade-report.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/ReportCommandResult", 4 | "definitions": { 5 | "ReportCommandResult": { 6 | "anyOf": [ 7 | { 8 | "$ref": "#/definitions/PackagePushRequestReportResult" 9 | }, 10 | { 11 | "type": "null" 12 | } 13 | ] 14 | }, 15 | "PackagePushRequestReportResult": { 16 | "type": "object", 17 | "properties": { 18 | "PackageVersion": { 19 | "type": "object", 20 | "properties": { 21 | "MetadataPackage": { 22 | "type": "object", 23 | "properties": { 24 | "Name": { 25 | "type": "string" 26 | }, 27 | "NamespacePrefix": { 28 | "type": "string" 29 | } 30 | }, 31 | "required": [ 32 | "Name", 33 | "NamespacePrefix" 34 | ], 35 | "additionalProperties": false 36 | }, 37 | "MetadataPackageId": { 38 | "type": "string" 39 | }, 40 | "Name": { 41 | "type": "string" 42 | }, 43 | "MajorVersion": { 44 | "type": "string" 45 | }, 46 | "MinorVersion": { 47 | "type": "string" 48 | } 49 | }, 50 | "required": [ 51 | "MetadataPackage", 52 | "MetadataPackageId", 53 | "Name", 54 | "MajorVersion", 55 | "MinorVersion" 56 | ], 57 | "additionalProperties": false 58 | }, 59 | "Id": { 60 | "type": "string" 61 | }, 62 | "PackageVersionId": { 63 | "type": "string" 64 | }, 65 | "Status": { 66 | "type": "string" 67 | }, 68 | "ScheduledStartTime": { 69 | "type": [ 70 | "string", 71 | "null" 72 | ] 73 | }, 74 | "StartTime": { 75 | "type": [ 76 | "string", 77 | "null" 78 | ] 79 | }, 80 | "EndTime": { 81 | "type": [ 82 | "string", 83 | "null" 84 | ] 85 | }, 86 | "DurationSeconds": { 87 | "type": [ 88 | "number", 89 | "null" 90 | ] 91 | } 92 | }, 93 | "required": [ 94 | "PackageVersion", 95 | "Id", 96 | "PackageVersionId", 97 | "Status", 98 | "ScheduledStartTime", 99 | "StartTime", 100 | "EndTime", 101 | "DurationSeconds" 102 | ], 103 | "additionalProperties": false 104 | } 105 | } 106 | } -------------------------------------------------------------------------------- /schemas/package-push__upgrade-schedule.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/PackagePushScheduleResult", 4 | "definitions": { 5 | "PackagePushScheduleResult": { 6 | "type": "object", 7 | "properties": { 8 | "PushRequestId": { 9 | "type": "string" 10 | }, 11 | "ScheduledStartTime": { 12 | "type": "string" 13 | }, 14 | "Status": { 15 | "type": "string" 16 | } 17 | }, 18 | "required": [ 19 | "PushRequestId", 20 | "Status" 21 | ], 22 | "additionalProperties": false 23 | } 24 | } 25 | } -------------------------------------------------------------------------------- /schemas/package-uninstall-report.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/PackagingSObjects.SubscriberPackageVersionUninstallRequest", 4 | "definitions": { 5 | "PackagingSObjects.SubscriberPackageVersionUninstallRequest": { 6 | "type": "object", 7 | "properties": { 8 | "Id": { 9 | "type": "string" 10 | }, 11 | "IsDeleted": { 12 | "type": "boolean" 13 | }, 14 | "CreatedDate": { 15 | "type": "number" 16 | }, 17 | "CreatedById": { 18 | "type": "string" 19 | }, 20 | "LastModifiedDate": { 21 | "type": "number" 22 | }, 23 | "LastModifiedById": { 24 | "type": "string" 25 | }, 26 | "SystemModstamp": { 27 | "type": "number" 28 | }, 29 | "SubscriberPackageVersionId": { 30 | "type": "string" 31 | }, 32 | "Status": { 33 | "type": "string", 34 | "enum": ["Error", "InProgress", "Queued", "Success"] 35 | } 36 | }, 37 | "required": [ 38 | "Id", 39 | "IsDeleted", 40 | "CreatedDate", 41 | "CreatedById", 42 | "LastModifiedDate", 43 | "LastModifiedById", 44 | "SystemModstamp", 45 | "SubscriberPackageVersionId", 46 | "Status" 47 | ], 48 | "additionalProperties": false 49 | } 50 | } 51 | } 52 | -------------------------------------------------------------------------------- /schemas/package-uninstall.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/UninstallResult", 4 | "definitions": { 5 | "UninstallResult": { 6 | "$ref": "#/definitions/PackagingSObjects.SubscriberPackageVersionUninstallRequest" 7 | }, 8 | "PackagingSObjects.SubscriberPackageVersionUninstallRequest": { 9 | "type": "object", 10 | "properties": { 11 | "Id": { 12 | "type": "string" 13 | }, 14 | "IsDeleted": { 15 | "type": "boolean" 16 | }, 17 | "CreatedDate": { 18 | "type": "number" 19 | }, 20 | "CreatedById": { 21 | "type": "string" 22 | }, 23 | "LastModifiedDate": { 24 | "type": "number" 25 | }, 26 | "LastModifiedById": { 27 | "type": "string" 28 | }, 29 | "SystemModstamp": { 30 | "type": "number" 31 | }, 32 | "SubscriberPackageVersionId": { 33 | "type": "string" 34 | }, 35 | "Status": { 36 | "type": "string", 37 | "enum": ["Error", "InProgress", "Queued", "Success"] 38 | } 39 | }, 40 | "required": [ 41 | "Id", 42 | "IsDeleted", 43 | "CreatedDate", 44 | "CreatedById", 45 | "LastModifiedDate", 46 | "LastModifiedById", 47 | "SystemModstamp", 48 | "SubscriberPackageVersionId", 49 | "Status" 50 | ], 51 | "additionalProperties": false 52 | } 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /schemas/package-update.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/PackageSaveResult", 4 | "definitions": { 5 | "PackageSaveResult": { 6 | "$ref": "#/definitions/SaveResult" 7 | }, 8 | "SaveResult": { 9 | "anyOf": [ 10 | { 11 | "type": "object", 12 | "properties": { 13 | "success": { 14 | "type": "boolean", 15 | "const": true 16 | }, 17 | "id": { 18 | "type": "string" 19 | }, 20 | "errors": { 21 | "type": "array", 22 | "items": { 23 | "not": {} 24 | } 25 | } 26 | }, 27 | "required": ["success", "id", "errors"], 28 | "additionalProperties": false 29 | }, 30 | { 31 | "type": "object", 32 | "properties": { 33 | "success": { 34 | "type": "boolean", 35 | "const": false 36 | }, 37 | "id": { 38 | "not": {} 39 | }, 40 | "errors": { 41 | "type": "array", 42 | "items": { 43 | "$ref": "#/definitions/SaveError" 44 | } 45 | } 46 | }, 47 | "required": ["success", "errors"], 48 | "additionalProperties": false 49 | } 50 | ] 51 | }, 52 | "SaveError": { 53 | "type": "object", 54 | "properties": { 55 | "errorCode": { 56 | "type": "string" 57 | }, 58 | "message": { 59 | "type": "string" 60 | }, 61 | "fields": { 62 | "type": "array", 63 | "items": { 64 | "type": "string" 65 | } 66 | } 67 | }, 68 | "required": ["errorCode", "message"], 69 | "additionalProperties": false 70 | } 71 | } 72 | } 73 | -------------------------------------------------------------------------------- /schemas/package-version-create-list.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/CreateListCommandResult", 4 | "definitions": { 5 | "CreateListCommandResult": { 6 | "type": "array", 7 | "items": { 8 | "type": "object", 9 | "additionalProperties": false, 10 | "properties": { 11 | "VersionName": { 12 | "type": "string" 13 | }, 14 | "VersionNumber": { 15 | "type": ["string", "null"] 16 | }, 17 | "Id": { 18 | "type": "string" 19 | }, 20 | "Status": { 21 | "$ref": "#/definitions/PackagingSObjects.Package2VersionStatus" 22 | }, 23 | "Package2Id": { 24 | "type": "string" 25 | }, 26 | "Package2Name": { 27 | "type": ["string", "null"] 28 | }, 29 | "Package2VersionId": { 30 | "type": "string" 31 | }, 32 | "SubscriberPackageVersionId": { 33 | "type": ["string", "null"] 34 | }, 35 | "Tag": { 36 | "type": "string" 37 | }, 38 | "Branch": { 39 | "type": "string" 40 | }, 41 | "Error": { 42 | "type": "array", 43 | "items": {} 44 | }, 45 | "CreatedDate": { 46 | "type": "string" 47 | }, 48 | "HasMetadataRemoved": { 49 | "type": ["boolean", "null"] 50 | }, 51 | "HasPassedCodeCoverageCheck": { 52 | "type": ["boolean", "null"] 53 | }, 54 | "CodeCoverage": { 55 | "type": ["number", "null"] 56 | }, 57 | "CreatedBy": { 58 | "type": "string" 59 | }, 60 | "ConvertedFromVersionId": { 61 | "type": ["string", "null"] 62 | }, 63 | "TotalNumberOfMetadataFiles": { 64 | "type": ["number", "null"] 65 | }, 66 | "TotalSizeOfMetadataFiles": { 67 | "type": ["number", "null"] 68 | } 69 | }, 70 | "required": [ 71 | "Branch", 72 | "CodeCoverage", 73 | "ConvertedFromVersionId", 74 | "CreatedBy", 75 | "CreatedDate", 76 | "Error", 77 | "HasMetadataRemoved", 78 | "HasPassedCodeCoverageCheck", 79 | "Id", 80 | "Package2Id", 81 | "Package2Name", 82 | "Package2VersionId", 83 | "Status", 84 | "SubscriberPackageVersionId", 85 | "Tag", 86 | "TotalNumberOfMetadataFiles", 87 | "TotalSizeOfMetadataFiles", 88 | "VersionNumber" 89 | ] 90 | } 91 | }, 92 | "PackagingSObjects.Package2VersionStatus": { 93 | "type": "string", 94 | "enum": [ 95 | "Queued", 96 | "InProgress", 97 | "Success", 98 | "Error", 99 | "Initializing", 100 | "VerifyingFeaturesAndSettings", 101 | "VerifyingDependencies", 102 | "VerifyingMetadata", 103 | "FinalizingPackageVersion", 104 | "PerformingValidations" 105 | ] 106 | } 107 | } 108 | } 109 | -------------------------------------------------------------------------------- /schemas/package-version-create-report.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/ReportCommandResult", 4 | "definitions": { 5 | "ReportCommandResult": { 6 | "type": "array", 7 | "items": { 8 | "$ref": "#/definitions/PackageVersionCreateRequestResult" 9 | } 10 | }, 11 | "PackageVersionCreateRequestResult": { 12 | "type": "object", 13 | "properties": { 14 | "Id": { 15 | "type": "string" 16 | }, 17 | "Status": { 18 | "$ref": "#/definitions/PackagingSObjects.Package2VersionStatus" 19 | }, 20 | "Package2Id": { 21 | "type": "string" 22 | }, 23 | "Package2Name": { 24 | "type": ["string", "null"] 25 | }, 26 | "Package2VersionId": { 27 | "type": "string" 28 | }, 29 | "SubscriberPackageVersionId": { 30 | "type": ["string", "null"] 31 | }, 32 | "Tag": { 33 | "type": "string" 34 | }, 35 | "Branch": { 36 | "type": "string" 37 | }, 38 | "Error": { 39 | "type": "array", 40 | "items": {} 41 | }, 42 | "CreatedDate": { 43 | "type": "string" 44 | }, 45 | "HasMetadataRemoved": { 46 | "type": ["boolean", "null"] 47 | }, 48 | "HasPassedCodeCoverageCheck": { 49 | "type": ["boolean", "null"] 50 | }, 51 | "CodeCoverage": { 52 | "type": ["number", "null"] 53 | }, 54 | "VersionNumber": { 55 | "type": ["string", "null"] 56 | }, 57 | "CreatedBy": { 58 | "type": "string" 59 | }, 60 | "ConvertedFromVersionId": { 61 | "type": ["string", "null"] 62 | }, 63 | "TotalNumberOfMetadataFiles": { 64 | "type": ["number", "null"] 65 | }, 66 | "TotalSizeOfMetadataFiles": { 67 | "type": ["number", "null"] 68 | } 69 | }, 70 | "required": [ 71 | "Id", 72 | "Status", 73 | "Package2Id", 74 | "Package2Name", 75 | "Package2VersionId", 76 | "SubscriberPackageVersionId", 77 | "Tag", 78 | "Branch", 79 | "Error", 80 | "CreatedDate", 81 | "HasMetadataRemoved", 82 | "HasPassedCodeCoverageCheck", 83 | "CodeCoverage", 84 | "VersionNumber", 85 | "CreatedBy", 86 | "ConvertedFromVersionId", 87 | "TotalNumberOfMetadataFiles", 88 | "TotalSizeOfMetadataFiles" 89 | ], 90 | "additionalProperties": false 91 | }, 92 | "PackagingSObjects.Package2VersionStatus": { 93 | "type": "string", 94 | "enum": [ 95 | "Queued", 96 | "InProgress", 97 | "Success", 98 | "Error", 99 | "Initializing", 100 | "VerifyingFeaturesAndSettings", 101 | "VerifyingDependencies", 102 | "VerifyingMetadata", 103 | "FinalizingPackageVersion", 104 | "PerformingValidations" 105 | ] 106 | } 107 | } 108 | } 109 | -------------------------------------------------------------------------------- /schemas/package-version-create.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/PackageVersionCommandResult", 4 | "definitions": { 5 | "PackageVersionCommandResult": { 6 | "type": "object", 7 | "properties": { 8 | "Id": { 9 | "type": "string" 10 | }, 11 | "Status": { 12 | "$ref": "#/definitions/PackagingSObjects.Package2VersionStatus" 13 | }, 14 | "Package2Id": { 15 | "type": "string" 16 | }, 17 | "Package2Name": { 18 | "type": ["string", "null"] 19 | }, 20 | "Package2VersionId": { 21 | "type": "string" 22 | }, 23 | "SubscriberPackageVersionId": { 24 | "type": ["string", "null"] 25 | }, 26 | "Tag": { 27 | "type": "string" 28 | }, 29 | "Branch": { 30 | "type": "string" 31 | }, 32 | "Error": { 33 | "type": "array", 34 | "items": {} 35 | }, 36 | "CreatedDate": { 37 | "type": "string" 38 | }, 39 | "HasMetadataRemoved": { 40 | "type": ["boolean", "null"] 41 | }, 42 | "HasPassedCodeCoverageCheck": { 43 | "type": ["boolean", "null"] 44 | }, 45 | "CodeCoverage": { 46 | "type": ["number", "null"] 47 | }, 48 | "VersionNumber": { 49 | "type": ["string", "null"] 50 | }, 51 | "CreatedBy": { 52 | "type": "string" 53 | }, 54 | "ConvertedFromVersionId": { 55 | "type": ["string", "null"] 56 | }, 57 | "TotalNumberOfMetadataFiles": { 58 | "type": ["number", "null"] 59 | }, 60 | "TotalSizeOfMetadataFiles": { 61 | "type": ["number", "null"] 62 | } 63 | }, 64 | "additionalProperties": false 65 | }, 66 | "PackagingSObjects.Package2VersionStatus": { 67 | "type": "string", 68 | "enum": [ 69 | "Queued", 70 | "InProgress", 71 | "Success", 72 | "Error", 73 | "Initializing", 74 | "VerifyingFeaturesAndSettings", 75 | "VerifyingDependencies", 76 | "VerifyingMetadata", 77 | "FinalizingPackageVersion", 78 | "PerformingValidations" 79 | ] 80 | } 81 | } 82 | } 83 | -------------------------------------------------------------------------------- /schemas/package-version-delete.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/PackageSaveResult", 4 | "definitions": { 5 | "PackageSaveResult": { 6 | "$ref": "#/definitions/SaveResult" 7 | }, 8 | "SaveResult": { 9 | "anyOf": [ 10 | { 11 | "type": "object", 12 | "properties": { 13 | "success": { 14 | "type": "boolean", 15 | "const": true 16 | }, 17 | "id": { 18 | "type": "string" 19 | }, 20 | "errors": { 21 | "type": "array", 22 | "items": { 23 | "not": {} 24 | } 25 | } 26 | }, 27 | "required": ["success", "id", "errors"], 28 | "additionalProperties": false 29 | }, 30 | { 31 | "type": "object", 32 | "properties": { 33 | "success": { 34 | "type": "boolean", 35 | "const": false 36 | }, 37 | "id": { 38 | "not": {} 39 | }, 40 | "errors": { 41 | "type": "array", 42 | "items": { 43 | "$ref": "#/definitions/SaveError" 44 | } 45 | } 46 | }, 47 | "required": ["success", "errors"], 48 | "additionalProperties": false 49 | } 50 | ] 51 | }, 52 | "SaveError": { 53 | "type": "object", 54 | "properties": { 55 | "errorCode": { 56 | "type": "string" 57 | }, 58 | "message": { 59 | "type": "string" 60 | }, 61 | "fields": { 62 | "type": "array", 63 | "items": { 64 | "type": "string" 65 | } 66 | } 67 | }, 68 | "required": ["errorCode", "message"], 69 | "additionalProperties": false 70 | } 71 | } 72 | } 73 | -------------------------------------------------------------------------------- /schemas/package-version-displayancestry.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/DisplayAncestryCommandResult", 4 | "definitions": { 5 | "DisplayAncestryCommandResult": { 6 | "anyOf": [ 7 | { 8 | "$ref": "#/definitions/PackageAncestryNodeData" 9 | }, 10 | { 11 | "type": "string" 12 | }, 13 | { 14 | "type": "null" 15 | } 16 | ] 17 | }, 18 | "PackageAncestryNodeData": { 19 | "type": "object", 20 | "properties": { 21 | "data": { 22 | "$ref": "#/definitions/PackageAncestryNodeOptions" 23 | }, 24 | "children": { 25 | "type": "array", 26 | "items": { 27 | "$ref": "#/definitions/PackageAncestryNodeData" 28 | } 29 | } 30 | }, 31 | "required": ["data", "children"], 32 | "additionalProperties": false 33 | }, 34 | "PackageAncestryNodeOptions": { 35 | "type": "object", 36 | "properties": { 37 | "AncestorId": { 38 | "type": "string" 39 | }, 40 | "SubscriberPackageVersionId": { 41 | "type": "string" 42 | }, 43 | "MajorVersion": { 44 | "type": ["string", "number"] 45 | }, 46 | "MinorVersion": { 47 | "type": ["string", "number"] 48 | }, 49 | "PatchVersion": { 50 | "type": ["string", "number"] 51 | }, 52 | "BuildNumber": { 53 | "type": ["string", "number"] 54 | }, 55 | "depthCounter": { 56 | "type": "number" 57 | } 58 | }, 59 | "required": [ 60 | "BuildNumber", 61 | "MajorVersion", 62 | "MinorVersion", 63 | "PatchVersion", 64 | "SubscriberPackageVersionId", 65 | "depthCounter" 66 | ] 67 | } 68 | } 69 | } 70 | -------------------------------------------------------------------------------- /schemas/package-version-list.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/PackageVersionListCommandResult", 4 | "definitions": { 5 | "PackageVersionListCommandResult": { 6 | "type": "array", 7 | "items": { 8 | "$ref": "#/definitions/PackageVersionListDetails" 9 | } 10 | }, 11 | "PackageVersionListDetails": { 12 | "type": "object", 13 | "additionalProperties": false, 14 | "properties": { 15 | "HasMetadataRemoved": { 16 | "type": "string" 17 | }, 18 | "IsPasswordProtected": { 19 | "type": ["string", "boolean"] 20 | }, 21 | "IsReleased": { 22 | "type": ["string", "boolean"] 23 | }, 24 | "HasPassedCodeCoverageCheck": { 25 | "type": ["string", "boolean"] 26 | }, 27 | "BuildDurationInSeconds": { 28 | "type": ["string", "number"] 29 | }, 30 | "CodeCoverage": { 31 | "type": "string" 32 | }, 33 | "NamespacePrefix": { 34 | "type": "string" 35 | }, 36 | "Package2Name": { 37 | "type": "string" 38 | }, 39 | "Version": { 40 | "type": "string" 41 | }, 42 | "InstallUrl": { 43 | "type": "string" 44 | }, 45 | "AncestorVersion": { 46 | "type": "string" 47 | }, 48 | "Alias": { 49 | "type": "string" 50 | }, 51 | "IsOrgDependent": { 52 | "type": "string", 53 | "enum": ["N/A", "Yes", "No"] 54 | }, 55 | "CreatedBy": { 56 | "type": "string" 57 | }, 58 | "ValidatedAsync": { 59 | "type": "boolean" 60 | }, 61 | "Id": { 62 | "type": "string" 63 | }, 64 | "Package2Id": { 65 | "type": "string" 66 | }, 67 | "SubscriberPackageVersionId": { 68 | "type": "string" 69 | }, 70 | "Name": { 71 | "type": "string" 72 | }, 73 | "Description": { 74 | "type": "string" 75 | }, 76 | "Tag": { 77 | "type": "string" 78 | }, 79 | "Branch": { 80 | "type": "string" 81 | }, 82 | "MajorVersion": { 83 | "type": "string" 84 | }, 85 | "MinorVersion": { 86 | "type": "string" 87 | }, 88 | "PatchVersion": { 89 | "type": "string" 90 | }, 91 | "BuildNumber": { 92 | "type": "string" 93 | }, 94 | "CreatedDate": { 95 | "type": "string" 96 | }, 97 | "LastModifiedDate": { 98 | "type": "string" 99 | }, 100 | "AncestorId": { 101 | "type": "string" 102 | }, 103 | "ValidationSkipped": { 104 | "type": "boolean" 105 | }, 106 | "ConvertedFromVersionId": { 107 | "type": "string" 108 | }, 109 | "ReleaseVersion": { 110 | "type": "string" 111 | }, 112 | "Language": { 113 | "type": "string" 114 | } 115 | }, 116 | "required": [ 117 | "Alias", 118 | "AncestorId", 119 | "AncestorVersion", 120 | "Branch", 121 | "BuildDurationInSeconds", 122 | "BuildNumber", 123 | "CodeCoverage", 124 | "CreatedBy", 125 | "CreatedDate", 126 | "Description", 127 | "HasMetadataRemoved", 128 | "HasPassedCodeCoverageCheck", 129 | "Id", 130 | "InstallUrl", 131 | "IsOrgDependent", 132 | "IsPasswordProtected", 133 | "IsReleased", 134 | "LastModifiedDate", 135 | "MajorVersion", 136 | "MinorVersion", 137 | "Name", 138 | "NamespacePrefix", 139 | "Package2Id", 140 | "Package2Name", 141 | "PatchVersion", 142 | "SubscriberPackageVersionId", 143 | "Tag", 144 | "ValidationSkipped", 145 | "Version" 146 | ] 147 | } 148 | } 149 | } 150 | -------------------------------------------------------------------------------- /schemas/package-version-promote.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/PackageSaveResult", 4 | "definitions": { 5 | "PackageSaveResult": { 6 | "$ref": "#/definitions/SaveResult" 7 | }, 8 | "SaveResult": { 9 | "anyOf": [ 10 | { 11 | "type": "object", 12 | "properties": { 13 | "success": { 14 | "type": "boolean", 15 | "const": true 16 | }, 17 | "id": { 18 | "type": "string" 19 | }, 20 | "errors": { 21 | "type": "array", 22 | "items": { 23 | "not": {} 24 | } 25 | } 26 | }, 27 | "required": ["success", "id", "errors"], 28 | "additionalProperties": false 29 | }, 30 | { 31 | "type": "object", 32 | "properties": { 33 | "success": { 34 | "type": "boolean", 35 | "const": false 36 | }, 37 | "id": { 38 | "not": {} 39 | }, 40 | "errors": { 41 | "type": "array", 42 | "items": { 43 | "$ref": "#/definitions/SaveError" 44 | } 45 | } 46 | }, 47 | "required": ["success", "errors"], 48 | "additionalProperties": false 49 | } 50 | ] 51 | }, 52 | "SaveError": { 53 | "type": "object", 54 | "properties": { 55 | "errorCode": { 56 | "type": "string" 57 | }, 58 | "message": { 59 | "type": "string" 60 | }, 61 | "fields": { 62 | "type": "array", 63 | "items": { 64 | "type": "string" 65 | } 66 | } 67 | }, 68 | "required": ["errorCode", "message"], 69 | "additionalProperties": false 70 | } 71 | } 72 | } 73 | -------------------------------------------------------------------------------- /schemas/package-version-retrieve.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/PackageVersionRetrieveCommandResult", 4 | "definitions": { 5 | "PackageVersionRetrieveCommandResult": { 6 | "type": "array", 7 | "items": { 8 | "$ref": "#/definitions/FileDownloadEntry" 9 | } 10 | }, 11 | "FileDownloadEntry": { 12 | "type": "object", 13 | "properties": { 14 | "fullName": { 15 | "type": "string" 16 | }, 17 | "type": { 18 | "type": "string" 19 | }, 20 | "filePath": { 21 | "type": "string" 22 | } 23 | }, 24 | "required": ["fullName", "type", "filePath"], 25 | "additionalProperties": false 26 | } 27 | } 28 | } 29 | -------------------------------------------------------------------------------- /schemas/package-version-update.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/PackageSaveResult", 4 | "definitions": { 5 | "PackageSaveResult": { 6 | "$ref": "#/definitions/SaveResult" 7 | }, 8 | "SaveResult": { 9 | "anyOf": [ 10 | { 11 | "type": "object", 12 | "properties": { 13 | "success": { 14 | "type": "boolean", 15 | "const": true 16 | }, 17 | "id": { 18 | "type": "string" 19 | }, 20 | "errors": { 21 | "type": "array", 22 | "items": { 23 | "not": {} 24 | } 25 | } 26 | }, 27 | "required": ["success", "id", "errors"], 28 | "additionalProperties": false 29 | }, 30 | { 31 | "type": "object", 32 | "properties": { 33 | "success": { 34 | "type": "boolean", 35 | "const": false 36 | }, 37 | "id": { 38 | "not": {} 39 | }, 40 | "errors": { 41 | "type": "array", 42 | "items": { 43 | "$ref": "#/definitions/SaveError" 44 | } 45 | } 46 | }, 47 | "required": ["success", "errors"], 48 | "additionalProperties": false 49 | } 50 | ] 51 | }, 52 | "SaveError": { 53 | "type": "object", 54 | "properties": { 55 | "errorCode": { 56 | "type": "string" 57 | }, 58 | "message": { 59 | "type": "string" 60 | }, 61 | "fields": { 62 | "type": "array", 63 | "items": { 64 | "type": "string" 65 | } 66 | } 67 | }, 68 | "required": ["errorCode", "message"], 69 | "additionalProperties": false 70 | } 71 | } 72 | } 73 | -------------------------------------------------------------------------------- /schemas/package1-version-create-get.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/PackagingSObjects.PackageUploadRequest", 4 | "definitions": { 5 | "PackagingSObjects.PackageUploadRequest": { 6 | "type": "object", 7 | "properties": { 8 | "Id": { 9 | "type": "string" 10 | }, 11 | "IsDeleted": { 12 | "type": "boolean" 13 | }, 14 | "CreatedDate": { 15 | "type": "number" 16 | }, 17 | "CreatedById": { 18 | "type": "string" 19 | }, 20 | "LastModifiedDate": { 21 | "type": "number" 22 | }, 23 | "LastModifiedById": { 24 | "type": "string" 25 | }, 26 | "SystemModstamp": { 27 | "type": "number" 28 | }, 29 | "MetadataPackageId": { 30 | "type": "string" 31 | }, 32 | "MetadataPackageVersionId": { 33 | "type": "string" 34 | }, 35 | "IsReleaseVersion": { 36 | "type": "boolean" 37 | }, 38 | "VersionName": { 39 | "type": "string" 40 | }, 41 | "Description": { 42 | "type": "string" 43 | }, 44 | "MajorVersion": { 45 | "type": "number" 46 | }, 47 | "MinorVersion": { 48 | "type": "number" 49 | }, 50 | "ReleaseNotesUrl": { 51 | "type": "string" 52 | }, 53 | "PostInstallUrl": { 54 | "type": "string" 55 | }, 56 | "Password": { 57 | "type": "string" 58 | }, 59 | "Status": { 60 | "type": "string" 61 | }, 62 | "Errors": { 63 | "type": "array", 64 | "items": {} 65 | } 66 | }, 67 | "required": [ 68 | "Id", 69 | "IsDeleted", 70 | "CreatedDate", 71 | "CreatedById", 72 | "LastModifiedDate", 73 | "LastModifiedById", 74 | "SystemModstamp", 75 | "MetadataPackageId", 76 | "MetadataPackageVersionId", 77 | "IsReleaseVersion", 78 | "VersionName", 79 | "Description", 80 | "MajorVersion", 81 | "MinorVersion", 82 | "ReleaseNotesUrl", 83 | "PostInstallUrl", 84 | "Password", 85 | "Status", 86 | "Errors" 87 | ], 88 | "additionalProperties": false 89 | } 90 | } 91 | } 92 | -------------------------------------------------------------------------------- /schemas/package1-version-create.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/PackageUploadRequest", 4 | "definitions": { 5 | "PackageUploadRequest": { 6 | "$ref": "#/definitions/PackagingSObjects.PackageUploadRequest" 7 | }, 8 | "PackagingSObjects.PackageUploadRequest": { 9 | "type": "object", 10 | "properties": { 11 | "Id": { 12 | "type": "string" 13 | }, 14 | "IsDeleted": { 15 | "type": "boolean" 16 | }, 17 | "CreatedDate": { 18 | "type": "number" 19 | }, 20 | "CreatedById": { 21 | "type": "string" 22 | }, 23 | "LastModifiedDate": { 24 | "type": "number" 25 | }, 26 | "LastModifiedById": { 27 | "type": "string" 28 | }, 29 | "SystemModstamp": { 30 | "type": "number" 31 | }, 32 | "MetadataPackageId": { 33 | "type": "string" 34 | }, 35 | "MetadataPackageVersionId": { 36 | "type": "string" 37 | }, 38 | "IsReleaseVersion": { 39 | "type": "boolean" 40 | }, 41 | "VersionName": { 42 | "type": "string" 43 | }, 44 | "Description": { 45 | "type": "string" 46 | }, 47 | "MajorVersion": { 48 | "type": "number" 49 | }, 50 | "MinorVersion": { 51 | "type": "number" 52 | }, 53 | "ReleaseNotesUrl": { 54 | "type": "string" 55 | }, 56 | "PostInstallUrl": { 57 | "type": "string" 58 | }, 59 | "Password": { 60 | "type": "string" 61 | }, 62 | "Status": { 63 | "type": "string" 64 | }, 65 | "Errors": { 66 | "type": "array", 67 | "items": {} 68 | } 69 | }, 70 | "required": [ 71 | "Id", 72 | "IsDeleted", 73 | "CreatedDate", 74 | "CreatedById", 75 | "LastModifiedDate", 76 | "LastModifiedById", 77 | "SystemModstamp", 78 | "MetadataPackageId", 79 | "MetadataPackageVersionId", 80 | "IsReleaseVersion", 81 | "VersionName", 82 | "Description", 83 | "MajorVersion", 84 | "MinorVersion", 85 | "ReleaseNotesUrl", 86 | "PostInstallUrl", 87 | "Password", 88 | "Status", 89 | "Errors" 90 | ], 91 | "additionalProperties": false 92 | } 93 | } 94 | } 95 | -------------------------------------------------------------------------------- /schemas/package1-version-display.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/Package1DisplayCommandResult", 4 | "definitions": { 5 | "Package1DisplayCommandResult": { 6 | "type": "array", 7 | "items": { 8 | "$ref": "#/definitions/Package1Display" 9 | } 10 | }, 11 | "Package1Display": { 12 | "type": "object", 13 | "properties": { 14 | "MetadataPackageVersionId": { 15 | "type": "string" 16 | }, 17 | "MetadataPackageId": { 18 | "type": "string" 19 | }, 20 | "Name": { 21 | "type": "string" 22 | }, 23 | "Version": { 24 | "type": "string" 25 | }, 26 | "ReleaseState": { 27 | "type": "string" 28 | }, 29 | "BuildNumber": { 30 | "type": "number" 31 | } 32 | }, 33 | "required": ["MetadataPackageVersionId", "MetadataPackageId", "Name", "Version", "ReleaseState", "BuildNumber"], 34 | "additionalProperties": false 35 | } 36 | } 37 | } 38 | -------------------------------------------------------------------------------- /schemas/package1-version-list.json: -------------------------------------------------------------------------------- 1 | { 2 | "$schema": "http://json-schema.org/draft-07/schema#", 3 | "$ref": "#/definitions/Package1ListCommandResult", 4 | "definitions": { 5 | "Package1ListCommandResult": { 6 | "type": "array", 7 | "items": { 8 | "$ref": "#/definitions/Package1Display" 9 | } 10 | }, 11 | "Package1Display": { 12 | "type": "object", 13 | "properties": { 14 | "MetadataPackageVersionId": { 15 | "type": "string" 16 | }, 17 | "MetadataPackageId": { 18 | "type": "string" 19 | }, 20 | "Name": { 21 | "type": "string" 22 | }, 23 | "Version": { 24 | "type": "string" 25 | }, 26 | "ReleaseState": { 27 | "type": "string" 28 | }, 29 | "BuildNumber": { 30 | "type": "number" 31 | } 32 | }, 33 | "required": ["MetadataPackageVersionId", "MetadataPackageId", "Name", "Version", "ReleaseState", "BuildNumber"], 34 | "additionalProperties": false 35 | } 36 | } 37 | } 38 | -------------------------------------------------------------------------------- /src/commands/package/create.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { Flags, loglevel, orgApiVersionFlagWithDeprecations, SfCommand } from '@salesforce/sf-plugins-core'; 9 | import { Messages } from '@salesforce/core/messages'; 10 | import { Package, PackageCreateOptions, PackageType } from '@salesforce/packaging'; 11 | import { requiredHubFlag } from '../../utils/hubFlag.js'; 12 | 13 | Messages.importMessagesDirectoryFromMetaUrl(import.meta.url); 14 | const messages = Messages.loadMessages('@salesforce/plugin-packaging', 'package_create'); 15 | 16 | export type PackageCreate = { Id: string }; 17 | export class PackageCreateCommand extends SfCommand { 18 | public static readonly summary = messages.getMessage('summary'); 19 | public static readonly description = messages.getMessage('description'); 20 | public static readonly examples = messages.getMessages('examples'); 21 | public static readonly deprecateAliases = true; 22 | public static readonly aliases = ['force:package:create']; 23 | public static readonly requiresProject = true; 24 | public static readonly flags = { 25 | loglevel, 26 | 'target-dev-hub': requiredHubFlag, 27 | 'api-version': orgApiVersionFlagWithDeprecations, 28 | name: Flags.string({ 29 | char: 'n', 30 | summary: messages.getMessage('flags.name.summary'), 31 | required: true, 32 | }), 33 | 'package-type': Flags.custom({ 34 | options: ['Managed', 'Unlocked'], 35 | })({ 36 | required: true, 37 | char: 't', 38 | deprecateAliases: true, 39 | aliases: ['packagetype'], 40 | summary: messages.getMessage('flags.package-type.summary'), 41 | description: messages.getMessage('flags.package-type.description'), 42 | }), 43 | description: Flags.string({ 44 | char: 'd', 45 | summary: messages.getMessage('flags.description.summary'), 46 | }), 47 | 'no-namespace': Flags.boolean({ 48 | char: 'e', 49 | deprecateAliases: true, 50 | aliases: ['nonamespace'], 51 | summary: messages.getMessage('flags.no-namespace.summary'), 52 | description: messages.getMessage('flags.no-namespace.description'), 53 | }), 54 | path: Flags.directory({ 55 | char: 'r', 56 | summary: messages.getMessage('flags.path.summary'), 57 | required: true, 58 | }), 59 | 'org-dependent': Flags.boolean({ 60 | deprecateAliases: true, 61 | aliases: ['orgdependent'], 62 | summary: messages.getMessage('flags.org-dependent.summary'), 63 | description: messages.getMessage('flags.org-dependent.description'), 64 | }), 65 | 'error-notification-username': Flags.string({ 66 | // eslint-disable-next-line sf-plugin/dash-o 67 | char: 'o', 68 | deprecateAliases: true, 69 | aliases: ['errornotificationusername'], 70 | summary: messages.getMessage('flags.error-notification-username.summary'), 71 | description: messages.getMessage('flags.error-notification-username.description'), 72 | }), 73 | }; 74 | 75 | public async run(): Promise { 76 | const { flags } = await this.parse(PackageCreateCommand); 77 | const options: PackageCreateOptions = { 78 | description: flags.description ?? '', 79 | errorNotificationUsername: flags['error-notification-username'] as string, 80 | name: flags.name, 81 | noNamespace: flags['no-namespace'], 82 | orgDependent: flags['org-dependent'], 83 | packageType: flags['package-type'], 84 | path: flags.path, 85 | }; 86 | const result: PackageCreate = await Package.create( 87 | flags['target-dev-hub'].getConnection(flags['api-version']), 88 | this.project!, 89 | options 90 | ); 91 | this.display(result); 92 | return result; 93 | } 94 | 95 | private display(result: PackageCreate): void { 96 | this.table({ data: [{ name: 'Package Id', value: result.Id }], title: 'Ids' }); 97 | } 98 | } 99 | -------------------------------------------------------------------------------- /src/commands/package/delete.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { Flags, loglevel, orgApiVersionFlagWithDeprecations, SfCommand } from '@salesforce/sf-plugins-core'; 9 | import { Messages } from '@salesforce/core/messages'; 10 | import { Package, PackageSaveResult } from '@salesforce/packaging'; 11 | import { requiredHubFlag } from '../../utils/hubFlag.js'; 12 | import { maybeGetProject } from '../../utils/getProject.js'; 13 | 14 | Messages.importMessagesDirectoryFromMetaUrl(import.meta.url); 15 | const messages = Messages.loadMessages('@salesforce/plugin-packaging', 'package_delete'); 16 | 17 | export class PackageDeleteCommand extends SfCommand { 18 | public static readonly summary = messages.getMessage('summary'); 19 | public static readonly description = messages.getMessage('description'); 20 | public static readonly examples = messages.getMessages('examples'); 21 | public static readonly deprecateAliases = true; 22 | public static readonly aliases = ['force:package:delete']; 23 | public static readonly flags = { 24 | loglevel, 25 | 'target-dev-hub': requiredHubFlag, 26 | 'api-version': orgApiVersionFlagWithDeprecations, 27 | 'no-prompt': Flags.boolean({ 28 | char: 'n', 29 | deprecateAliases: true, 30 | aliases: ['noprompt'], 31 | summary: messages.getMessage('flags.no-prompt.summary'), 32 | }), 33 | package: Flags.string({ 34 | char: 'p', 35 | summary: messages.getMessage('flags.package.summary'), 36 | required: true, 37 | }), 38 | undelete: Flags.boolean({ 39 | summary: messages.getMessage('flags.undelete.summary'), 40 | hidden: true, 41 | default: false, 42 | }), 43 | }; 44 | 45 | public async run(): Promise { 46 | const { flags } = await this.parse(PackageDeleteCommand); 47 | const message = messages.getMessage(flags.undelete ? 'prompt-undelete' : 'prompt-delete'); 48 | const accepted = flags['no-prompt'] || flags.json ? true : await this.confirm({ message }); 49 | if (!accepted) { 50 | throw messages.createError('prompt-delete-deny'); 51 | } 52 | 53 | const pkg = new Package({ 54 | connection: flags['target-dev-hub'].getConnection(flags['api-version']), 55 | project: await maybeGetProject(), 56 | packageAliasOrId: flags.package, 57 | }); 58 | const result = flags.undelete ? await pkg.undelete() : await pkg.delete(); 59 | this.display(result, flags.undelete); 60 | return result; 61 | } 62 | 63 | private display(result: PackageSaveResult, undelete: boolean): void { 64 | this.log(); 65 | this.logSuccess(messages.getMessage(undelete ? 'humanSuccessUndelete' : 'humanSuccess', [result.id])); 66 | } 67 | } 68 | -------------------------------------------------------------------------------- /src/commands/package/install/report.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { 9 | Flags, 10 | loglevel, 11 | orgApiVersionFlagWithDeprecations, 12 | requiredOrgFlagWithDeprecations, 13 | SfCommand, 14 | } from '@salesforce/sf-plugins-core'; 15 | import { Messages, Org } from '@salesforce/core'; 16 | import { PackagingSObjects, SubscriberPackageVersion } from '@salesforce/packaging'; 17 | 18 | export type PackageInstallRequest = PackagingSObjects.PackageInstallRequest; 19 | 20 | Messages.importMessagesDirectoryFromMetaUrl(import.meta.url); 21 | const messages = Messages.loadMessages('@salesforce/plugin-packaging', 'package_install_report'); 22 | const installMsgs = Messages.loadMessages('@salesforce/plugin-packaging', 'package_install'); 23 | 24 | export class Report extends SfCommand { 25 | public static readonly summary = messages.getMessage('summary'); 26 | public static readonly examples = messages.getMessages('examples'); 27 | public static readonly deprecateAliases = true; 28 | public static readonly aliases = ['force:package:install:report']; 29 | public static org: Org; 30 | 31 | public static readonly flags = { 32 | 'target-org': requiredOrgFlagWithDeprecations, 33 | 'api-version': orgApiVersionFlagWithDeprecations, 34 | loglevel, 35 | 'request-id': Flags.salesforceId({ 36 | startsWith: '0Hf', 37 | length: 'both', 38 | char: 'i', 39 | deprecateAliases: true, 40 | aliases: ['requestid'], 41 | summary: messages.getMessage('flags.request-id.summary'), 42 | required: true, 43 | }), 44 | }; 45 | 46 | public static parseStatus(binName: string, request: PackageInstallRequest, username: string, alias?: string): string { 47 | const pkgIdOrAlias = alias ?? request.SubscriberPackageVersionKey; 48 | const { Status } = request; 49 | if (Status === 'SUCCESS') { 50 | return installMsgs.getMessage('package-install-success', [pkgIdOrAlias]); 51 | } else if (['IN_PROGRESS', 'UNKNOWN'].includes(Status)) { 52 | return installMsgs.getMessage('packageInstallInProgress', [binName, request.Id, username]); 53 | } else { 54 | let errorMessage = ''; 55 | const errors = request?.Errors?.errors; 56 | if (errors?.length) { 57 | errorMessage = 'Installation errors: '; 58 | for (let i = 0; i < errors.length; i++) { 59 | errorMessage += `\n${i + 1}) ${errors[i].message}`; 60 | } 61 | } 62 | throw installMsgs.createError('packageInstallError', [errorMessage]); 63 | } 64 | } 65 | 66 | public async run(): Promise { 67 | const { flags } = await this.parse(Report); 68 | const connection = flags['target-org'].getConnection(flags['api-version']); 69 | const pkgInstallRequest = await SubscriberPackageVersion.getInstallRequest(flags['request-id'], connection); 70 | this.log(Report.parseStatus(this.config.bin, pkgInstallRequest, flags['target-org'].getUsername() as string)); 71 | 72 | return pkgInstallRequest; 73 | } 74 | } 75 | -------------------------------------------------------------------------------- /src/commands/package/installed/list.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { Messages } from '@salesforce/core/messages'; 9 | import { 10 | loglevel, 11 | orgApiVersionFlagWithDeprecations, 12 | requiredOrgFlagWithDeprecations, 13 | SfCommand, 14 | } from '@salesforce/sf-plugins-core'; 15 | import { InstalledPackages, SubscriberPackageVersion } from '@salesforce/packaging'; 16 | 17 | Messages.importMessagesDirectoryFromMetaUrl(import.meta.url); 18 | const messages = Messages.loadMessages('@salesforce/plugin-packaging', 'package_installed_list'); 19 | 20 | export type PackageInstalledListResult = { 21 | Id: string; 22 | SubscriberPackageId?: string; 23 | SubscriberPackageName?: string; 24 | SubscriberPackageNamespace?: string; 25 | SubscriberPackageVersionId?: string; 26 | SubscriberPackageVersionName?: string; 27 | SubscriberPackageVersionNumber?: string; 28 | }; 29 | 30 | export type PackageInstalledCommandResult = PackageInstalledListResult[]; 31 | 32 | export class PackageInstalledListCommand extends SfCommand { 33 | public static readonly summary = messages.getMessage('summary'); 34 | public static readonly examples = messages.getMessages('examples'); 35 | public static readonly deprecateAliases = true; 36 | public static readonly aliases = ['force:package:installed:list']; 37 | 38 | public static readonly flags = { 39 | loglevel, 40 | 'target-org': requiredOrgFlagWithDeprecations, 41 | 'api-version': orgApiVersionFlagWithDeprecations, 42 | }; 43 | 44 | public async run(): Promise { 45 | const { flags } = await this.parse(PackageInstalledListCommand); 46 | const records = ( 47 | await SubscriberPackageVersion.installedList(flags['target-org'].getConnection(flags['api-version'])) 48 | ).map(transformRow); 49 | 50 | this.table({ 51 | data: records, 52 | columns: [ 53 | { key: 'Id', name: 'ID' }, 54 | { key: 'SubscriberPackageId', name: 'Package ID' }, 55 | { key: 'SubscriberPackageName', name: 'Package Name' }, 56 | { key: 'SubscriberPackageNamespace', name: 'Namespace' }, 57 | { key: 'SubscriberPackageVersionId', name: 'Package Version ID' }, 58 | { key: 'SubscriberPackageVersionName', name: 'Version Name' }, 59 | { key: 'SubscriberPackageVersionNumber', name: 'Version' }, 60 | ], 61 | overflow: 'wrap', 62 | }); 63 | 64 | return records; 65 | } 66 | } 67 | 68 | const transformRow = (r: InstalledPackages): PackageInstalledListResult => ({ 69 | Id: r.Id, 70 | SubscriberPackageId: r.SubscriberPackageId, 71 | ...(r.SubscriberPackage 72 | ? { 73 | SubscriberPackageName: r.SubscriberPackage.Name, 74 | SubscriberPackageNamespace: r.SubscriberPackage.NamespacePrefix, 75 | } 76 | : {}), 77 | ...(r.SubscriberPackageVersion 78 | ? { 79 | SubscriberPackageVersionId: r.SubscriberPackageVersion.Id, 80 | SubscriberPackageVersionName: r.SubscriberPackageVersion.Name, 81 | SubscriberPackageVersionNumber: `${r.SubscriberPackageVersion.MajorVersion}.${r.SubscriberPackageVersion.MinorVersion}.${r.SubscriberPackageVersion.PatchVersion}.${r.SubscriberPackageVersion.BuildNumber}`, 82 | } 83 | : {}), 84 | }); 85 | -------------------------------------------------------------------------------- /src/commands/package/list.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { Flags, loglevel, orgApiVersionFlagWithDeprecations, SfCommand } from '@salesforce/sf-plugins-core'; 9 | import { Messages } from '@salesforce/core/messages'; 10 | import { Package, PackagingSObjects } from '@salesforce/packaging'; 11 | import chalk from 'chalk'; 12 | import { SfProject } from '@salesforce/core'; 13 | import { requiredHubFlag } from '../../utils/hubFlag.js'; 14 | 15 | Messages.importMessagesDirectoryFromMetaUrl(import.meta.url); 16 | const messages = Messages.loadMessages('@salesforce/plugin-packaging', 'package_list'); 17 | 18 | export type Package2Result = Required> & 19 | Partial< 20 | Pick< 21 | PackagingSObjects.Package2, 22 | | 'SubscriberPackageId' 23 | | 'Description' 24 | | 'NamespacePrefix' 25 | | 'ContainerOptions' 26 | | 'ConvertedFromPackageId' 27 | | 'PackageErrorUsername' 28 | | 'AppAnalyticsEnabled' 29 | > & { 30 | Alias: string; 31 | CreatedBy: string; 32 | IsOrgDependent: string; 33 | } 34 | >; 35 | 36 | export type PackageListCommandResult = Package2Result[]; 37 | 38 | export class PackageListCommand extends SfCommand { 39 | public static readonly summary = messages.getMessage('summary'); 40 | public static readonly description = messages.getMessage('description'); 41 | public static readonly examples = messages.getMessages('examples'); 42 | public static readonly deprecateAliases = true; 43 | public static readonly aliases = ['force:package:list']; 44 | public static readonly flags = { 45 | loglevel, 46 | 'target-dev-hub': requiredHubFlag, 47 | 'api-version': orgApiVersionFlagWithDeprecations, 48 | verbose: Flags.boolean({ 49 | summary: messages.getMessage('flags.verbose.summary'), 50 | }), 51 | }; 52 | 53 | public async run(): Promise { 54 | const { flags } = await this.parse(PackageListCommand); 55 | const connection = flags['target-dev-hub'].getConnection(flags['api-version']); 56 | const queryResult = await Package.list(connection); 57 | const results = mapRecordsToResults(queryResult); 58 | this.displayResults(results, flags.verbose, connection.getApiVersion()); 59 | return results; 60 | } 61 | 62 | private displayResults(results: Package2Result[], verbose = false, apiVersion: string): void { 63 | const data = results.map((r) => ({ 64 | 'Namespace Prefix': r.NamespacePrefix, 65 | Name: r.Name, 66 | Id: r.Id, 67 | Alias: r.Alias, 68 | Description: r.Description, 69 | ContainerOptions: r.ContainerOptions, 70 | ...(verbose 71 | ? { 72 | 'Package Id': r.SubscriberPackageId, 73 | 'Converted From Package Id': r.ConvertedFromPackageId, 74 | 'Org-Dependent Unlocked Package': r.IsOrgDependent, 75 | 'Error Notification Username': r.PackageErrorUsername, 76 | 'Created By': r.CreatedBy, 77 | ...(parseInt(apiVersion, 10) >= 59 ? { 'App Analytics Enabled': r.AppAnalyticsEnabled } : {}), 78 | } 79 | : {}), 80 | })); 81 | this.table({ data, title: chalk.blue(`Packages [${results.length}]`) }); 82 | } 83 | } 84 | 85 | const mapRecordsToResults = (records: PackagingSObjects.Package2[], project?: SfProject): Package2Result[] => 86 | records 87 | .filter((record) => record.IsDeprecated === false) 88 | .map( 89 | ({ 90 | Id, 91 | SubscriberPackageId, 92 | Name, 93 | Description, 94 | NamespacePrefix, 95 | ContainerOptions, 96 | ConvertedFromPackageId, 97 | IsOrgDependent, 98 | PackageErrorUsername, 99 | AppAnalyticsEnabled, 100 | CreatedById, 101 | }) => ({ 102 | Id, 103 | SubscriberPackageId, 104 | Name, 105 | Description, 106 | NamespacePrefix, 107 | ContainerOptions, 108 | ConvertedFromPackageId, 109 | Alias: project ? project.getAliasesFromPackageId(Id).join() : '', 110 | IsOrgDependent: ContainerOptions === 'Managed' ? 'N/A' : IsOrgDependent ? 'Yes' : 'No', 111 | PackageErrorUsername, 112 | AppAnalyticsEnabled, 113 | CreatedBy: CreatedById, 114 | }) 115 | ); 116 | -------------------------------------------------------------------------------- /src/commands/package/push-upgrade/abort.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2024, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | import { Flags, SfCommand } from '@salesforce/sf-plugins-core'; 8 | import { Messages } from '@salesforce/core'; 9 | import { PackagePushUpgrade } from '@salesforce/packaging'; 10 | 11 | Messages.importMessagesDirectoryFromMetaUrl(import.meta.url); 12 | const messages = Messages.loadMessages('@salesforce/plugin-packaging', 'package_pushupgrade_abort'); 13 | 14 | export type PackagePushUpgradeAbortResult = { 15 | success: boolean; 16 | }; 17 | 18 | export class PackagePushUpgradeAbortCommand extends SfCommand { 19 | public static readonly summary = messages.getMessage('summary'); 20 | public static readonly description = messages.getMessage('description'); 21 | public static readonly examples = messages.getMessages('examples'); 22 | public static readonly flags = { 23 | 'target-dev-hub': Flags.requiredHub(), 24 | 'api-version': Flags.orgApiVersion(), 25 | 'push-request-id': Flags.salesforceId({ 26 | length: 'both', 27 | char: 'i', 28 | summary: messages.getMessage('flags.push-request-id.summary'), 29 | required: true, 30 | startsWith: '0DV', 31 | }), 32 | }; 33 | 34 | public async run(): Promise { 35 | const { flags } = await this.parse(PackagePushUpgradeAbortCommand); 36 | const connection = flags['target-dev-hub'].getConnection(flags['api-version']); 37 | 38 | const packagePushRequestOptions = { packagePushRequestId: flags['push-request-id'] }; 39 | 40 | const result: boolean = await PackagePushUpgrade.abort(connection, packagePushRequestOptions); 41 | 42 | if (result) { 43 | this.log(messages.getMessage('output', [flags['push-request-id']])); 44 | } 45 | 46 | return { success: result }; 47 | } 48 | } 49 | -------------------------------------------------------------------------------- /src/commands/package/push-upgrade/schedule.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2024, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | import * as fs from 'node:fs/promises'; 8 | import { Flags, SfCommand, orgApiVersionFlagWithDeprecations } from '@salesforce/sf-plugins-core'; 9 | import { Messages, SfError, Logger } from '@salesforce/core'; 10 | import { PackagePushScheduleResult, PackagePushUpgrade } from '@salesforce/packaging'; 11 | 12 | Messages.importMessagesDirectoryFromMetaUrl(import.meta.url); 13 | const messages = Messages.loadMessages('@salesforce/plugin-packaging', 'package_pushupgrade_schedule'); 14 | 15 | export class PackagePushScheduleCommand extends SfCommand { 16 | public static readonly summary = messages.getMessage('summary'); 17 | public static readonly description = messages.getMessage('description'); 18 | public static readonly examples = messages.getMessages('examples'); 19 | public static readonly flags = { 20 | 'target-dev-hub': Flags.requiredHub({ 21 | char: 'v', 22 | summary: messages.getMessage('flags.target-dev-hub.summary'), 23 | description: messages.getMessage('flags.target-dev-hub.description'), 24 | required: true, 25 | }), 26 | 'api-version': orgApiVersionFlagWithDeprecations, 27 | package: Flags.salesforceId({ 28 | char: 'p', 29 | length: 'both', 30 | startsWith: '04t', 31 | summary: messages.getMessage('flags.package.summary'), 32 | required: true, 33 | }), 34 | 'start-time': Flags.string({ 35 | char: 't', 36 | summary: messages.getMessage('flags.start-time.summary'), 37 | description: messages.getMessage('flags.start-time.description'), 38 | }), 39 | 'org-list': Flags.string({ 40 | char: 'l', 41 | summary: messages.getMessage('flags.org-list.summary'), 42 | exclusive: ['org-file'], 43 | }), 44 | 'org-file': Flags.file({ 45 | char: 'f', 46 | summary: messages.getMessage('flags.org-file.summary'), 47 | description: messages.getMessage('flags.org-file.description'), 48 | exists: true, 49 | exclusive: ['org-list'], 50 | }), 51 | 'migrate-to-2gp': Flags.boolean({ 52 | summary: messages.getMessage('flags.migrate-to-2gp.summary'), 53 | }), 54 | }; 55 | 56 | public async run(): Promise { 57 | const { flags } = await this.parse(PackagePushScheduleCommand); 58 | const logger = await Logger.child(this.constructor.name); 59 | let orgList: string[] = []; 60 | 61 | if (flags['org-file']) { 62 | logger.debug(`Reading org list from file: ${flags['org-file']}`); 63 | orgList = await readOrgFile(flags['org-file']); 64 | } else if (flags['org-list']) { 65 | logger.debug('Using org list from input flag.'); 66 | orgList = getOrgListFromInput(flags['org-list']); 67 | } else { 68 | throw new SfError(messages.getMessage('error.no-org-file-or-org-list-input')); 69 | } 70 | 71 | const conn = flags['target-dev-hub'].getConnection(flags['api-version']); 72 | 73 | const startTime = flags['start-time']; 74 | const isMigration = flags['migrate-to-2gp']; 75 | 76 | const result: PackagePushScheduleResult = await PackagePushUpgrade.schedule( 77 | conn, 78 | flags.package, 79 | startTime, 80 | orgList, 81 | isMigration 82 | ); 83 | 84 | this.log(messages.getMessage('output', [result?.PushRequestId, orgList.join(', ')])); 85 | 86 | return result; 87 | } 88 | } 89 | 90 | async function readOrgFile(filePath: string): Promise { 91 | try { 92 | const fileContent = await fs.readFile(filePath, 'utf-8'); 93 | const orgIds = fileContent.split(/\r?\n/).filter((id) => id.trim().length > 0); 94 | 95 | return orgIds.filter((id: string) => /^00D[a-zA-Z0-9]{12}$/.test(id)); 96 | } catch (error) { 97 | throw new SfError(messages.getMessage('error.invalid-org-file')); 98 | } 99 | } 100 | 101 | function getOrgListFromInput(orgInput: string): string[] { 102 | try { 103 | if (orgInput.length === 0) { 104 | throw new SfError(messages.getMessage('error.empty-org-input')); 105 | } 106 | 107 | const orgList = orgInput.split(',').map((org) => org.trim()); 108 | 109 | return orgList.filter((org) => org.length > 0); 110 | } catch (error) { 111 | throw new SfError(messages.getMessage('error.invalid-org-input')); 112 | } 113 | } 114 | -------------------------------------------------------------------------------- /src/commands/package/uninstall.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { 9 | Flags, 10 | loglevel, 11 | orgApiVersionFlagWithDeprecations, 12 | requiredOrgFlagWithDeprecations, 13 | SfCommand, 14 | } from '@salesforce/sf-plugins-core'; 15 | import { Lifecycle, Messages } from '@salesforce/core'; 16 | import { PackageEvents, PackagingSObjects, SubscriberPackageVersion } from '@salesforce/packaging'; 17 | import { Duration } from '@salesforce/kit'; 18 | 19 | export type UninstallResult = PackagingSObjects.SubscriberPackageVersionUninstallRequest; 20 | 21 | Messages.importMessagesDirectoryFromMetaUrl(import.meta.url); 22 | const messages = Messages.loadMessages('@salesforce/plugin-packaging', 'package_uninstall'); 23 | 24 | export class PackageUninstallCommand extends SfCommand { 25 | public static readonly summary = messages.getMessage('summary'); 26 | public static readonly description = messages.getMessage('description'); 27 | public static readonly examples = messages.getMessages('examples'); 28 | public static readonly deprecateAliases = true; 29 | public static readonly aliases = ['force:package:uninstall']; 30 | public static readonly flags = { 31 | loglevel, 32 | 'target-org': requiredOrgFlagWithDeprecations, 33 | 'api-version': orgApiVersionFlagWithDeprecations, 34 | wait: Flags.duration({ 35 | unit: 'minutes', 36 | char: 'w', 37 | summary: messages.getMessage('flags.wait.summary'), 38 | default: Duration.minutes(0), 39 | }), 40 | package: Flags.string({ 41 | char: 'p', 42 | summary: messages.getMessage('flags.package.summary'), 43 | required: true, 44 | }), 45 | }; 46 | 47 | public async run(): Promise { 48 | const { flags } = await this.parse(PackageUninstallCommand); 49 | // no awaits in async method 50 | // eslint-disable-next-line @typescript-eslint/require-await 51 | Lifecycle.getInstance().on(PackageEvents.uninstall, async (data: UninstallResult) => { 52 | // Request still in progress. Just print a console message and move on. Server will be polled again. 53 | this.log(`Waiting for the package uninstall request to get processed. Status = ${data.Status}`); 54 | }); 55 | 56 | const packageVersion = new SubscriberPackageVersion({ 57 | aliasOrId: flags.package, 58 | connection: flags['target-org'].getConnection(flags['api-version']), 59 | password: undefined, 60 | }); 61 | 62 | const result = await packageVersion.uninstall(Duration.seconds(30), flags.wait); 63 | 64 | const arg = 65 | result.Status === 'Success' 66 | ? [result.SubscriberPackageVersionId] 67 | : [this.config.bin, result.Id, flags['target-org'].getUsername()]; 68 | this.log(messages.getMessage(result.Status, arg)); 69 | 70 | return result; 71 | } 72 | } 73 | -------------------------------------------------------------------------------- /src/commands/package/uninstall/report.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { 9 | Flags, 10 | loglevel, 11 | orgApiVersionFlagWithDeprecations, 12 | requiredOrgFlagWithDeprecations, 13 | SfCommand, 14 | } from '@salesforce/sf-plugins-core'; 15 | import { Messages } from '@salesforce/core/messages'; 16 | import { PackagingSObjects, SubscriberPackageVersion } from '@salesforce/packaging'; 17 | 18 | Messages.importMessagesDirectoryFromMetaUrl(import.meta.url); 19 | const messages = Messages.loadMessages('@salesforce/plugin-packaging', 'package_uninstall_report'); 20 | 21 | export class PackageUninstallReportCommand extends SfCommand { 22 | public static readonly summary = messages.getMessage('summary'); 23 | public static readonly examples = messages.getMessages('examples'); 24 | public static readonly deprecateAliases = true; 25 | public static readonly aliases = ['force:package:uninstall:report']; 26 | public static readonly flags = { 27 | loglevel, 28 | 'target-org': requiredOrgFlagWithDeprecations, 29 | 'api-version': orgApiVersionFlagWithDeprecations, 30 | // eslint-disable-next-line sf-plugin/id-flag-suggestions 31 | 'request-id': Flags.salesforceId({ 32 | length: 'both', 33 | deprecateAliases: true, 34 | aliases: ['requestid'], 35 | char: 'i', 36 | summary: messages.getMessage('flags.request-id.summary'), 37 | required: true, 38 | startsWith: '06y', 39 | }), 40 | }; 41 | 42 | public async run(): Promise { 43 | const { flags } = await this.parse(PackageUninstallReportCommand); 44 | const result = await SubscriberPackageVersion.uninstallStatus( 45 | flags['request-id'], 46 | flags['target-org'].getConnection(flags['api-version']) 47 | ); 48 | 49 | const arg = 50 | result.Status === 'Success' 51 | ? [result.SubscriberPackageVersionId] 52 | : [this.config.bin, result.Id, flags['target-org'].getUsername()]; 53 | this.log(messages.getMessage(result.Status, arg)); 54 | 55 | return result; 56 | } 57 | } 58 | -------------------------------------------------------------------------------- /src/commands/package/update.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { Flags, loglevel, orgApiVersionFlagWithDeprecations, SfCommand } from '@salesforce/sf-plugins-core'; 9 | import { Messages } from '@salesforce/core/messages'; 10 | import { Package, PackageSaveResult } from '@salesforce/packaging'; 11 | import { requiredHubFlag } from '../../utils/hubFlag.js'; 12 | import { maybeGetProject } from '../../utils/getProject.js'; 13 | 14 | Messages.importMessagesDirectoryFromMetaUrl(import.meta.url); 15 | const messages = Messages.loadMessages('@salesforce/plugin-packaging', 'package_update'); 16 | const packageCreate = Messages.loadMessages('@salesforce/plugin-packaging', 'package_create'); 17 | 18 | export class PackageUpdateCommand extends SfCommand { 19 | public static readonly summary = messages.getMessage('summary'); 20 | public static readonly description = messages.getMessage('description'); 21 | public static readonly examples = messages.getMessages('examples'); 22 | public static readonly deprecateAliases = true; 23 | public static readonly aliases = ['force:package:update']; 24 | public static readonly flags = { 25 | loglevel, 26 | 'target-dev-hub': requiredHubFlag, 27 | 'api-version': orgApiVersionFlagWithDeprecations, 28 | package: Flags.string({ 29 | char: 'p', 30 | summary: messages.getMessage('flags.package.summary'), 31 | required: true, 32 | }), 33 | name: Flags.string({ 34 | char: 'n', 35 | summary: messages.getMessage('flags.name.summary'), 36 | }), 37 | description: Flags.string({ 38 | char: 'd', 39 | summary: messages.getMessage('flags.description.summary'), 40 | }), 41 | 'error-notification-username': Flags.string({ 42 | // eslint-disable-next-line sf-plugin/dash-o 43 | char: 'o', 44 | deprecateAliases: true, 45 | aliases: ['errornotificationusername'], 46 | summary: packageCreate.getMessage('flags.error-notification-username.summary'), 47 | description: packageCreate.getMessage('flags.error-notification-username.description'), 48 | }), 49 | 'enable-app-analytics': Flags.boolean({ 50 | summary: messages.getMessage('flags.enable-app-analytics.summary'), 51 | allowNo: true, 52 | }), 53 | }; 54 | 55 | public async run(): Promise { 56 | const { flags } = await this.parse(PackageUpdateCommand); 57 | 58 | const pkg = new Package({ 59 | packageAliasOrId: flags.package, 60 | connection: flags['target-dev-hub'].getConnection(flags['api-version']), 61 | project: await maybeGetProject(), 62 | }); 63 | 64 | const result = await pkg.update({ 65 | Id: pkg.getId(), 66 | Name: flags.name, 67 | Description: flags.description, 68 | PackageErrorUsername: flags['error-notification-username'], 69 | AppAnalyticsEnabled: flags['enable-app-analytics'], 70 | }); 71 | 72 | this.logSuccess(messages.getMessage('success', [pkg.getId()])); 73 | 74 | return result; 75 | } 76 | } 77 | -------------------------------------------------------------------------------- /src/commands/package/version/delete.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { Flags, loglevel, orgApiVersionFlagWithDeprecations, SfCommand } from '@salesforce/sf-plugins-core'; 9 | import { Messages } from '@salesforce/core/messages'; 10 | import { PackageSaveResult, PackageVersion } from '@salesforce/packaging'; 11 | import { requiredHubFlag } from '../../../utils/hubFlag.js'; 12 | import { maybeGetProject } from '../../../utils/getProject.js'; 13 | 14 | Messages.importMessagesDirectoryFromMetaUrl(import.meta.url); 15 | const messages = Messages.loadMessages('@salesforce/plugin-packaging', 'package_version_delete'); 16 | 17 | export class PackageVersionDeleteCommand extends SfCommand { 18 | public static readonly summary = messages.getMessage('summary'); 19 | public static readonly description = messages.getMessage('description'); 20 | public static readonly examples = messages.getMessages('examples'); 21 | public static readonly deprecateAliases = true; 22 | public static readonly aliases = ['force:package:version:delete']; 23 | public static readonly flags = { 24 | loglevel, 25 | 'target-dev-hub': requiredHubFlag, 26 | 'api-version': orgApiVersionFlagWithDeprecations, 27 | 'no-prompt': Flags.boolean({ 28 | char: 'n', 29 | deprecateAliases: true, 30 | aliases: ['noprompt'], 31 | summary: messages.getMessage('flags.no-prompt.summary'), 32 | }), 33 | package: Flags.string({ 34 | char: 'p', 35 | summary: messages.getMessage('flags.package.summary'), 36 | required: true, 37 | }), 38 | undelete: Flags.boolean({ 39 | summary: messages.getMessage('flags.undelete.summary'), 40 | hidden: true, 41 | }), 42 | }; 43 | 44 | public async run(): Promise { 45 | const { flags } = await this.parse(PackageVersionDeleteCommand); 46 | const packageVersion = new PackageVersion({ 47 | connection: flags['target-dev-hub'].getConnection(flags['api-version']), 48 | project: await maybeGetProject(), 49 | idOrAlias: flags.package, 50 | }); 51 | await this.confirmDelete(flags['no-prompt'], flags.undelete); 52 | const results = flags.undelete ? await packageVersion.undelete() : await packageVersion.delete(); 53 | this.logSuccess(this.getHumanSuccessMessage(results, flags.undelete)); 54 | return results; 55 | } 56 | 57 | private async confirmDelete(noprompt: boolean, undelete: boolean): Promise { 58 | if (noprompt || this.jsonEnabled()) { 59 | return true; 60 | } 61 | const message = undelete ? messages.getMessage('prompt-undelete') : messages.getMessage('prompt-delete'); 62 | const accepted = await this.confirm({ message }); 63 | if (!accepted) { 64 | throw new Error(messages.getMessage('prompt-delete-deny')); 65 | } 66 | return true; 67 | } 68 | 69 | // eslint-disable-next-line class-methods-use-this 70 | private getHumanSuccessMessage(result: PackageSaveResult, undelete: boolean): string { 71 | return messages.getMessage(undelete ? 'humanSuccessUndelete' : 'humanSuccess', [result.id]); 72 | } 73 | } 74 | -------------------------------------------------------------------------------- /src/commands/package/version/displayancestry.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { Flags, loglevel, orgApiVersionFlagWithDeprecations, SfCommand } from '@salesforce/sf-plugins-core'; 9 | import { Messages } from '@salesforce/core/messages'; 10 | import { Package, PackageAncestryNodeData } from '@salesforce/packaging'; 11 | import { requiredHubFlag } from '../../../utils/hubFlag.js'; 12 | import { maybeGetProject } from '../../../utils/getProject.js'; 13 | 14 | // Import i18n messages 15 | Messages.importMessagesDirectoryFromMetaUrl(import.meta.url); 16 | const messages = Messages.loadMessages('@salesforce/plugin-packaging', 'package_displayancestry'); 17 | 18 | export type DisplayAncestryCommandResult = PackageAncestryNodeData | string | void; 19 | 20 | export class PackageVersionDisplayAncestryCommand extends SfCommand { 21 | public static readonly summary = messages.getMessage('summary'); 22 | public static readonly examples = messages.getMessages('examples'); 23 | public static readonly deprecateAliases = true; 24 | public static readonly aliases = ['force:package:version:displayancestry']; 25 | 26 | public static readonly flags = { 27 | loglevel, 28 | 'target-dev-hub': requiredHubFlag, 29 | 'api-version': orgApiVersionFlagWithDeprecations, 30 | package: Flags.string({ 31 | char: 'p', 32 | summary: messages.getMessage('flags.package.summary'), 33 | description: messages.getMessage('flags.package.description'), 34 | required: true, 35 | }), 36 | 'dot-code': Flags.boolean({ 37 | aliases: ['dotcode'], 38 | deprecateAliases: true, 39 | summary: messages.getMessage('flags.dot-code.summary'), 40 | description: messages.getMessage('flags.dot-code.description'), 41 | }), 42 | verbose: Flags.boolean({ 43 | summary: messages.getMessage('flags.verbose.summary'), 44 | }), 45 | }; 46 | 47 | public async run(): Promise { 48 | const { flags } = await this.parse(PackageVersionDisplayAncestryCommand); 49 | const packageAncestry = await Package.getAncestry( 50 | flags.package, 51 | await maybeGetProject(), 52 | flags['target-dev-hub'].getConnection(flags['api-version']) 53 | ); 54 | const jsonProducer = packageAncestry.getJsonProducer(); 55 | if (flags['dot-code']) { 56 | const dotProducer = packageAncestry.getDotProducer(); 57 | const dotCodeResult = dotProducer.produce(); 58 | if (flags.json) { 59 | return dotCodeResult; 60 | } else { 61 | this.log(dotCodeResult as string); 62 | } 63 | } else { 64 | if (packageAncestry.requestedPackageId?.startsWith('04t')) { 65 | const paths = packageAncestry.getLeafPathToRoot(packageAncestry.requestedPackageId); 66 | this.log(`${paths[0].map((p) => p.getVersion()).join(' -> ')} (root)`); 67 | this.log(); 68 | } 69 | const treeProducer = packageAncestry.getTreeProducer(flags.verbose); 70 | if (!flags.json) { 71 | treeProducer.produce(); 72 | } 73 | } 74 | return jsonProducer.produce(); 75 | } 76 | } 77 | -------------------------------------------------------------------------------- /src/commands/package/version/promote.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { Flags, loglevel, orgApiVersionFlagWithDeprecations, SfCommand } from '@salesforce/sf-plugins-core'; 9 | import { Messages, SfError } from '@salesforce/core'; 10 | import { PackageSaveResult, PackageVersion } from '@salesforce/packaging'; 11 | import { requiredHubFlag } from '../../../utils/hubFlag.js'; 12 | import { maybeGetProject } from '../../../utils/getProject.js'; 13 | 14 | Messages.importMessagesDirectoryFromMetaUrl(import.meta.url); 15 | const messages = Messages.loadMessages('@salesforce/plugin-packaging', 'package_version_promote'); 16 | 17 | export class PackageVersionPromoteCommand extends SfCommand { 18 | public static readonly summary = messages.getMessage('summary'); 19 | public static readonly description = messages.getMessage('description'); 20 | public static readonly deprecateAliases = true; 21 | public static readonly aliases = ['force:package:version:promote']; 22 | public static readonly examples = messages.getMessages('examples'); 23 | public static readonly flags = { 24 | loglevel, 25 | 'target-dev-hub': requiredHubFlag, 26 | 'api-version': orgApiVersionFlagWithDeprecations, 27 | package: Flags.string({ 28 | char: 'p', 29 | summary: messages.getMessage('flags.package.summary'), 30 | required: true, 31 | }), 32 | 'no-prompt': Flags.boolean({ 33 | char: 'n', 34 | deprecateAliases: true, 35 | aliases: ['noprompt'], 36 | summary: messages.getMessage('flags.no-prompt.summary'), 37 | }), 38 | }; 39 | 40 | public async run(): Promise { 41 | const { flags } = await this.parse(PackageVersionPromoteCommand); 42 | const packageVersion = new PackageVersion({ 43 | connection: flags['target-dev-hub'].getConnection(flags['api-version']), 44 | project: await maybeGetProject(), 45 | idOrAlias: flags.package, 46 | }); 47 | const packageVersionData = await packageVersion.getData(); 48 | 49 | if (!flags.json && !flags['no-prompt']) { 50 | // Warn when a Managed package has removed metadata 51 | if (packageVersionData.HasMetadataRemoved) { 52 | this.warn(messages.getMessage('hasMetadataRemovedWarning')); 53 | } 54 | 55 | // Prompt for confirmation 56 | if (!(await this.confirm({ message: messages.getMessage('packageVersionPromoteConfirm', [flags.package]) }))) { 57 | throw messages.createError('promote-deny'); 58 | } 59 | } 60 | 61 | try { 62 | const result = await packageVersion.promote(); 63 | result.id = packageVersionData.SubscriberPackageVersionId; 64 | this.log(messages.getMessage('humanSuccess', [result.id])); 65 | return result; 66 | } catch (e) { 67 | const err = SfError.wrap(e as Error); 68 | if (err.name === 'DUPLICATE_VALUE' && err.message.includes('previously released')) { 69 | err.message = messages.getMessage('previouslyReleasedMessage'); 70 | err.actions = [messages.getMessage('previouslyReleasedAction', [this.config.bin, this.config.bin])]; 71 | } 72 | throw err; 73 | } 74 | } 75 | } 76 | -------------------------------------------------------------------------------- /src/commands/package/version/retrieve.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import path from 'node:path'; 9 | import { 10 | Flags, 11 | loglevel, 12 | orgApiVersionFlagWithDeprecations, 13 | requiredOrgFlagWithDeprecations, 14 | SfCommand, 15 | } from '@salesforce/sf-plugins-core'; 16 | import { Messages } from '@salesforce/core/messages'; 17 | import { Package, PackageVersionMetadataDownloadResult } from '@salesforce/packaging'; 18 | 19 | Messages.importMessagesDirectoryFromMetaUrl(import.meta.url); 20 | const messages = Messages.loadMessages('@salesforce/plugin-packaging', 'package_version_retrieve'); 21 | 22 | export type FileDownloadEntry = { 23 | fullName: string; 24 | type: string; 25 | filePath: string; 26 | }; 27 | 28 | export type PackageVersionRetrieveCommandResult = FileDownloadEntry[]; 29 | 30 | export class PackageVersionRetrieveCommand extends SfCommand { 31 | public static readonly hidden = true; 32 | public static readonly summary = messages.getMessage('summary'); 33 | public static readonly description = messages.getMessage('description'); 34 | public static readonly examples = messages.getMessages('examples'); 35 | public static readonly requiresProject = true; 36 | public static readonly flags = { 37 | loglevel, 38 | 'api-version': orgApiVersionFlagWithDeprecations, 39 | 'target-org': requiredOrgFlagWithDeprecations, 40 | package: Flags.string({ 41 | char: 'p', 42 | summary: messages.getMessage('flags.package.summary'), 43 | required: true, 44 | }), 45 | 'output-dir': Flags.directory({ 46 | char: 'd', 47 | summary: messages.getMessage('flags.output-dir.summary'), 48 | default: 'force-app', 49 | }), 50 | }; 51 | 52 | public async run(): Promise { 53 | const { flags } = await this.parse(PackageVersionRetrieveCommand); 54 | const connection = flags['target-org'].getConnection(flags['api-version']); 55 | const options = { 56 | subscriberPackageVersionId: flags.package ?? '', 57 | destinationFolder: flags['output-dir'], 58 | }; 59 | 60 | const result: PackageVersionMetadataDownloadResult = await Package.downloadPackageVersionMetadata( 61 | this.project!, 62 | options, 63 | connection 64 | ); 65 | const results: PackageVersionRetrieveCommandResult = []; 66 | 67 | result.converted?.forEach((component) => { 68 | if (component.xml) { 69 | results.push({ 70 | fullName: component.fullName, 71 | type: component.type.name, 72 | filePath: path.relative('.', component.xml), 73 | }); 74 | } 75 | if (component.content) { 76 | results.push({ 77 | fullName: component.fullName, 78 | type: component.type.name, 79 | filePath: path.relative('.', component.content), 80 | }); 81 | } 82 | }); 83 | 84 | this.table({ 85 | data: results, 86 | columns: [ 87 | { key: 'fullName', name: messages.getMessage('headers.fullName') }, 88 | { key: 'type', name: messages.getMessage('headers.type') }, 89 | { key: 'filePath', name: messages.getMessage('headers.filePath') }, 90 | ], 91 | overflow: 'wrap', 92 | }); 93 | 94 | return results; 95 | } 96 | } 97 | -------------------------------------------------------------------------------- /src/commands/package/version/update.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { Flags, loglevel, orgApiVersionFlagWithDeprecations, SfCommand } from '@salesforce/sf-plugins-core'; 9 | import { Messages } from '@salesforce/core/messages'; 10 | import { PackageSaveResult, PackageVersion } from '@salesforce/packaging'; 11 | import { requiredHubFlag } from '../../../utils/hubFlag.js'; 12 | 13 | Messages.importMessagesDirectoryFromMetaUrl(import.meta.url); 14 | const messages = Messages.loadMessages('@salesforce/plugin-packaging', 'package_version_update'); 15 | 16 | export class PackageVersionUpdateCommand extends SfCommand { 17 | public static readonly summary = messages.getMessage('summary'); 18 | public static readonly description = messages.getMessage('description'); 19 | public static readonly examples = messages.getMessages('examples'); 20 | public static readonly deprecateAliases = true; 21 | public static readonly aliases = ['force:package:version:update']; 22 | public static readonly requiresProject = true; 23 | public static readonly flags = { 24 | loglevel, 25 | 'target-dev-hub': requiredHubFlag, 26 | 'api-version': orgApiVersionFlagWithDeprecations, 27 | package: Flags.string({ 28 | char: 'p', 29 | summary: messages.getMessage('flags.package.summary'), 30 | required: true, 31 | }), 32 | 'version-name': Flags.string({ 33 | aliases: ['versionname'], 34 | deprecateAliases: true, 35 | char: 'a', 36 | summary: messages.getMessage('flags.version-name.summary'), 37 | }), 38 | 'version-description': Flags.string({ 39 | aliases: ['versiondescription'], 40 | deprecateAliases: true, 41 | char: 'e', 42 | summary: messages.getMessage('flags.version-description.summary'), 43 | }), 44 | branch: Flags.string({ 45 | char: 'b', 46 | summary: messages.getMessage('flags.branch.summary'), 47 | }), 48 | tag: Flags.string({ 49 | char: 't', 50 | summary: messages.getMessage('flags.tag.summary'), 51 | }), 52 | 'installation-key': Flags.string({ 53 | aliases: ['installationkey'], 54 | deprecateAliases: true, 55 | char: 'k', 56 | summary: messages.getMessage('flags.installation-key.summary'), 57 | }), 58 | }; 59 | 60 | public async run(): Promise { 61 | const { flags } = await this.parse(PackageVersionUpdateCommand); 62 | const pv = new PackageVersion({ 63 | connection: flags['target-dev-hub'].getConnection(flags['api-version']), 64 | project: this.project!, 65 | idOrAlias: flags.package, 66 | }); 67 | const result = await pv.update({ 68 | VersionDescription: flags['version-description'], 69 | Branch: flags.branch, 70 | InstallKey: flags['installation-key'], 71 | VersionName: flags['version-name'], 72 | Tag: flags.tag, 73 | }); 74 | 75 | this.logSuccess(messages.getMessage('success', [result.id])); 76 | 77 | return result; 78 | } 79 | } 80 | -------------------------------------------------------------------------------- /src/commands/package1/version/create/get.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { 9 | Flags, 10 | loglevel, 11 | orgApiVersionFlagWithDeprecations, 12 | requiredOrgFlagWithDeprecations, 13 | SfCommand, 14 | } from '@salesforce/sf-plugins-core'; 15 | import { Messages } from '@salesforce/core/messages'; 16 | import { Package1Version, PackagingSObjects } from '@salesforce/packaging'; 17 | 18 | Messages.importMessagesDirectoryFromMetaUrl(import.meta.url); 19 | const messages = Messages.loadMessages('@salesforce/plugin-packaging', 'package1_version_create_get'); 20 | 21 | export class Package1VersionCreateGetCommand extends SfCommand { 22 | public static readonly summary = messages.getMessage('summary'); 23 | public static readonly examples = messages.getMessages('examples'); 24 | public static readonly deprecateAliases = true; 25 | public static readonly aliases = ['force:package1:version:create:get']; 26 | public static readonly flags = { 27 | loglevel, 28 | 'target-org': requiredOrgFlagWithDeprecations, 29 | 'api-version': orgApiVersionFlagWithDeprecations, 30 | 'request-id': Flags.salesforceId({ 31 | startsWith: '0HD', 32 | length: 'both', 33 | deprecateAliases: true, 34 | aliases: ['requestid'], 35 | char: 'i', 36 | summary: messages.getMessage('flags.request-id.summary'), 37 | required: true, 38 | }), 39 | }; 40 | 41 | public async run(): Promise { 42 | const { flags } = await this.parse(Package1VersionCreateGetCommand); 43 | const result = await Package1Version.getCreateStatus( 44 | flags['target-org'].getConnection(flags['api-version']), 45 | flags['request-id'] 46 | ); 47 | 48 | if (result.Status === 'ERROR') { 49 | // toolbelt was accessing request.Errors.errors, I'm unsure about this type, but was unable to reproduce an error 50 | // in the wild, and decided to trust how it was working 51 | const errors = (result.Errors as unknown as { errors: Error[] })?.errors?.map((e) => e.message).join('\n'); 52 | throw messages.createError('uploadFailure', [errors ?? 'Package version creation failed with unknown error']); 53 | } else { 54 | const arg = 55 | result.Status === 'SUCCESS' 56 | ? [result.MetadataPackageVersionId] 57 | : [this.config.bin, result.Id, flags['target-org'].getUsername()]; 58 | this.log(messages.getMessage(result.Status, arg)); 59 | } 60 | 61 | return result; 62 | } 63 | } 64 | -------------------------------------------------------------------------------- /src/commands/package1/version/display.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { 9 | Flags, 10 | loglevel, 11 | orgApiVersionFlagWithDeprecations, 12 | requiredOrgFlagWithDeprecations, 13 | SfCommand, 14 | } from '@salesforce/sf-plugins-core'; 15 | import { Messages } from '@salesforce/core/messages'; 16 | import { Package1Display, Package1Version } from '@salesforce/packaging'; 17 | 18 | Messages.importMessagesDirectoryFromMetaUrl(import.meta.url); 19 | const messages = Messages.loadMessages('@salesforce/plugin-packaging', 'package1_version_display'); 20 | 21 | export type Package1DisplayCommandResult = Package1Display[]; 22 | export class Package1VersionDisplayCommand extends SfCommand { 23 | public static readonly summary = messages.getMessage('summary'); 24 | public static readonly examples = messages.getMessages('examples'); 25 | public static readonly deprecateAliases = true; 26 | public static readonly aliases = ['force:package1:version:display']; 27 | 28 | public static readonly flags = { 29 | loglevel, 30 | 'target-org': requiredOrgFlagWithDeprecations, 31 | 'api-version': orgApiVersionFlagWithDeprecations, 32 | 'package-version-id': Flags.salesforceId({ 33 | length: 'both', 34 | char: 'i', 35 | deprecateAliases: true, 36 | aliases: ['packageversionid'], 37 | summary: messages.getMessage('flags.package-version-id.summary'), 38 | required: true, 39 | startsWith: '04t', 40 | }), 41 | }; 42 | 43 | public async run(): Promise { 44 | const { flags } = await this.parse(Package1VersionDisplayCommand); 45 | const pv1 = new Package1Version( 46 | flags['target-org'].getConnection(flags['api-version']), 47 | flags['package-version-id'] 48 | ); 49 | const data = (await pv1.getPackageVersion()).map((result) => ({ 50 | MetadataPackageVersionId: result.Id, 51 | MetadataPackageId: result.MetadataPackageId, 52 | Name: result.Name, 53 | ReleaseState: result.ReleaseState, 54 | Version: `${result.MajorVersion}.${result.MinorVersion}.${result.PatchVersion}`, 55 | BuildNumber: result.BuildNumber, 56 | })); 57 | 58 | if (data.length === 0) { 59 | this.warn('No results found'); 60 | } else { 61 | this.table({ data }); 62 | } 63 | 64 | return data; 65 | } 66 | } 67 | -------------------------------------------------------------------------------- /src/commands/package1/version/list.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { 9 | Flags, 10 | loglevel, 11 | orgApiVersionFlagWithDeprecations, 12 | requiredOrgFlagWithDeprecations, 13 | SfCommand, 14 | } from '@salesforce/sf-plugins-core'; 15 | import { Messages } from '@salesforce/core/messages'; 16 | import { Package1Display, Package1Version } from '@salesforce/packaging'; 17 | 18 | Messages.importMessagesDirectoryFromMetaUrl(import.meta.url); 19 | const messages = Messages.loadMessages('@salesforce/plugin-packaging', 'package1_version_list'); 20 | export type Package1ListCommandResult = Package1Display[]; 21 | export class Package1VersionListCommand extends SfCommand { 22 | public static readonly summary = messages.getMessage('summary'); 23 | public static readonly examples = messages.getMessages('examples'); 24 | public static readonly deprecateAliases = true; 25 | public static readonly aliases = ['force:package1:version:list']; 26 | public static readonly flags = { 27 | loglevel, 28 | 'target-org': requiredOrgFlagWithDeprecations, 29 | 'api-version': orgApiVersionFlagWithDeprecations, 30 | 'package-id': Flags.salesforceId({ 31 | length: 18, 32 | deprecateAliases: true, 33 | aliases: ['packageid'], 34 | char: 'i', 35 | summary: messages.getMessage('flags.package-id.summary'), 36 | description: messages.getMessage('flags.package-id.description'), 37 | startsWith: '033', 38 | }), 39 | }; 40 | 41 | public async run(): Promise { 42 | const { flags } = await this.parse(Package1VersionListCommand); 43 | const data = ( 44 | await Package1Version.list(flags['target-org'].getConnection(flags['api-version']), flags['package-id'] as string) 45 | ).map((record) => ({ 46 | MetadataPackageVersionId: record.Id, 47 | MetadataPackageId: record.MetadataPackageId, 48 | Name: record.Name, 49 | ReleaseState: record.ReleaseState, 50 | Version: `${record.MajorVersion}.${record.MinorVersion}.${record.PatchVersion}`, 51 | BuildNumber: record.BuildNumber, 52 | })); 53 | 54 | if (data.length) { 55 | this.table({ data }); 56 | } else { 57 | this.warn('No Results Found'); 58 | } 59 | return data; 60 | } 61 | } 62 | -------------------------------------------------------------------------------- /src/index.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | export default {}; 9 | -------------------------------------------------------------------------------- /src/utils/getProject.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { SfProject } from '@salesforce/core'; 9 | 10 | /* 11 | * Get the sfdx project from the current dir. 12 | * It will return `undefined` if there's no project. 13 | * */ 14 | export async function maybeGetProject(): Promise { 15 | try { 16 | return await SfProject.resolve(); 17 | } catch { 18 | return undefined; 19 | } 20 | } 21 | -------------------------------------------------------------------------------- /src/utils/hubFlag.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2023, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | import { Flags } from '@salesforce/sf-plugins-core'; 8 | 9 | /** 10 | * @deprecated 11 | */ 12 | export const requiredHubFlag = Flags.requiredHub({ 13 | aliases: ['targetdevhubusername', 'target-hub-org'], 14 | deprecateAliases: true, 15 | required: true, 16 | }); 17 | -------------------------------------------------------------------------------- /test/.eslintrc.cjs: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2021, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | module.exports = { 9 | extends: '../.eslintrc.cjs', 10 | // Allow describe and it 11 | env: { mocha: true }, 12 | rules: { 13 | // Allow assert style expressions. i.e. expect(true).to.be.true 14 | 'no-unused-expressions': 'off', 15 | 16 | // It is common for tests to stub out method. 17 | '@typescript-eslint/ban-ts-comment': 'off', 18 | // Return types are defined by the source code. Allows for quick overwrites. 19 | '@typescript-eslint/explicit-function-return-type': 'off', 20 | // Mocked out the methods that shouldn't do anything in the tests. 21 | '@typescript-eslint/no-empty-function': 'off', 22 | // Easily return a promise in a mocked method. 23 | '@typescript-eslint/require-await': 'off', 24 | '@typescript-eslint/prefer-nullish-coalescing': 'off', 25 | }, 26 | }; 27 | -------------------------------------------------------------------------------- /test/commands/package/install.nut.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import path from 'node:path'; 9 | import { execCmd, TestSession } from '@salesforce/cli-plugins-testkit'; 10 | import { expect } from 'chai'; 11 | import { PackagingSObjects } from '@salesforce/packaging'; 12 | import { Duration } from '@salesforce/kit'; 13 | 14 | type PackageInstallRequest = PackagingSObjects.PackageInstallRequest; 15 | type PackageUninstallRequest = PackagingSObjects.SubscriberPackageVersionUninstallRequest; 16 | 17 | describe('package install', () => { 18 | let session: TestSession; 19 | before(async () => { 20 | session = await TestSession.create({ 21 | devhubAuthStrategy: 'AUTO', 22 | scratchOrgs: [ 23 | { 24 | setDefault: true, 25 | config: path.join('config', 'project-scratch-def.json'), 26 | }, 27 | ], 28 | project: { name: 'packageInstall' }, 29 | }); 30 | }); 31 | 32 | after(async () => { 33 | await session?.clean(); 34 | }); 35 | 36 | it('should install ElectronBranding package with polling', () => { 37 | const command = 'package:install -p 04t6A000002zgKSQAY -w 20'; 38 | const output = execCmd(command, { ensureExitCode: 0, timeout: Duration.minutes(20).milliseconds }).shellOutput 39 | .stdout; 40 | expect(output).to.contain('Successfully installed package'); 41 | }); 42 | 43 | it('should install DFXP Escape Room package (async) and report', () => { 44 | const installCommand = 'package:install -p 04t6A000002zgKSQAY --json'; 45 | const installJson = execCmd(installCommand, { ensureExitCode: 0 }).jsonOutput?.result; 46 | expect(installJson).to.have.property('Status', 'IN_PROGRESS'); 47 | 48 | const reportCommand = `package:install:report -i ${installJson?.Id} --json`; 49 | const reportJson = execCmd(reportCommand, { ensureExitCode: 0 }).jsonOutput?.result; 50 | expect(reportJson).to.have.property('Status'); 51 | expect(['IN_PROGRESS', 'SUCCESS']).to.include(reportJson?.Status); 52 | }); 53 | 54 | it('should start an uninstall request, and report on it', () => { 55 | const uninstallCommand = 'package:uninstall -p 04t6A000002zgKSQAY --json -w 0'; 56 | const uninstallRequest = execCmd(uninstallCommand, { 57 | ensureExitCode: 0, 58 | }).jsonOutput?.result; 59 | expect(['InProgress', 'Success']).to.include(uninstallRequest?.Status); 60 | expect(uninstallRequest?.Id.startsWith('06y')).to.be.true; 61 | 62 | const uninstallReportCommand = `package:uninstall:report -i ${uninstallRequest?.Id} --json`; 63 | const uninstallReportResult = execCmd(uninstallReportCommand, { ensureExitCode: 0 }).jsonOutput?.result; 64 | expect(uninstallReportResult).to.have.all.keys( 65 | 'Id', 66 | 'IsDeleted', 67 | 'CreatedDate', 68 | 'CreatedById', 69 | 'LastModifiedDate', 70 | 'LastModifiedById', 71 | 'SystemModstamp', 72 | 'SubscriberPackageVersionId', 73 | 'Status', 74 | 'attributes' 75 | ); 76 | }); 77 | }); 78 | -------------------------------------------------------------------------------- /test/commands/package/packageCreateAndDelete.nut.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { execCmd, TestSession } from '@salesforce/cli-plugins-testkit'; 9 | import { expect } from 'chai'; 10 | import { Org } from '@salesforce/core'; 11 | 12 | describe('package create/update/delete', () => { 13 | let session: TestSession; 14 | let pkgName: string; 15 | let hubOrg: Org; 16 | let apiVersion: string; 17 | before(async () => { 18 | session = await TestSession.create({ 19 | devhubAuthStrategy: 'AUTO', 20 | project: { name: 'packageCreateDelete' }, 21 | }); 22 | hubOrg = await Org.create({ aliasOrUsername: session.hubOrg.username }); 23 | apiVersion = hubOrg.getConnection().getApiVersion(); 24 | }); 25 | 26 | after(async () => { 27 | await session?.clean(); 28 | }); 29 | describe('create/update/delete - human results', () => { 30 | before(async () => { 31 | pkgName = `test-pkg-${Date.now()}`; 32 | }); 33 | it('should create a package - human readable results', () => { 34 | const command = `package:create -n ${pkgName} -v ${session.hubOrg.username} -t Unlocked -r ./force-app`; 35 | const output = execCmd(command, { ensureExitCode: 0 }).shellOutput.stdout; 36 | expect(output).to.contain('Ids'); 37 | expect(output).to.match(/Package Id\s+?|0Ho/); 38 | }); 39 | it('should update a package - human readable results', () => { 40 | const command = `package:update --package ${pkgName} --description "My new description" -v ${session.hubOrg.username}`; 41 | const output = execCmd(command, { ensureExitCode: 0 }).shellOutput.stdout; 42 | expect(output).to.match(/Successfully updated the package\.\s+0Ho/); 43 | }); 44 | it('should not be able to enable app analytics on package that is not managed', () => { 45 | if (apiVersion >= '59.0') { 46 | const command = `package:update --package ${pkgName} --enable-app-analytics -v ${session.hubOrg.username}`; 47 | const errOut = execCmd(command, { ensureExitCode: 1 }).shellOutput.stderr; 48 | expect(errOut).to.contain('App Analytics is only available for managed packages'); 49 | } 50 | }); 51 | it('should delete a package - human readable results', () => { 52 | const command = `package:delete -p ${pkgName} -v ${session.hubOrg.username} --no-prompt`; 53 | const output = execCmd(command, { ensureExitCode: 0 }).shellOutput.stdout; 54 | expect(output).to.contain('Successfully deleted the package with ID: 0Ho'); 55 | }); 56 | }); 57 | describe('create/update/delete - json results', () => { 58 | before(async () => { 59 | pkgName = `test-pkg-${Date.now()}`; 60 | }); 61 | it('should create a package - json results', () => { 62 | const command = `package:create -n ${pkgName} -v ${session.hubOrg.username} -t Unlocked -r ./force-app --json`; 63 | const output = execCmd<{ Id: string }>(command, { ensureExitCode: 0 }).jsonOutput; 64 | expect(output?.status).to.equal(0); 65 | expect(output?.result).to.have.property('Id'); 66 | expect(output?.result?.Id).to.match(/0Ho.{12,15}/); 67 | }); 68 | it('should update a package - json results', () => { 69 | const command = `package:update --package ${pkgName} --description "My new description" -v ${session.hubOrg.username} --json`; 70 | const output = execCmd<{ id: string }>(command, { ensureExitCode: 0 }).jsonOutput; 71 | expect(output?.status).to.equal(0); 72 | expect(output?.result).to.have.property('id'); 73 | expect(output?.result?.id).to.match(/0Ho.{12,15}/); 74 | }); 75 | it('should delete a package - json results', () => { 76 | const command = `package:delete -p ${pkgName} -v ${session.hubOrg.username} --json`; 77 | const output = execCmd<{ id: string; success: boolean; errors: [] }>(command, { ensureExitCode: 0 }).jsonOutput; 78 | expect(output?.result?.id).to.match(/0Ho.{12,15}/); 79 | expect(output?.result?.success).to.be.true; 80 | }); 81 | }); 82 | }); 83 | -------------------------------------------------------------------------------- /test/commands/package/packageInstalledList.nut.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { execCmd, TestSession } from '@salesforce/cli-plugins-testkit'; 9 | import { expect } from 'chai'; 10 | import { PackageInstalledListResult } from '../../../src/commands/package/installed/list.js'; 11 | 12 | describe('package:installed:list', () => { 13 | let session: TestSession; 14 | 15 | // TODO: na40 required as DevHub 16 | before(async () => { 17 | session = await TestSession.create({ 18 | devhubAuthStrategy: 'AUTO', 19 | }); 20 | }); 21 | 22 | after(async () => { 23 | await session?.clean(); 24 | }); 25 | it('should list all installed packages in dev hub - human readable results', () => { 26 | const command = `package:installed:list -o ${session.hubOrg.username}`; 27 | const output = execCmd(command, { ensureExitCode: 0 }).shellOutput.stdout; 28 | expect(output).to.match( 29 | /ID\s+?|Package ID\s+?|Package Name\s+?|Namespace\s+?|Package Version ID\s+?|Version Name\s+?|Version/ 30 | ); 31 | }); 32 | 33 | it('should list all installed packages in dev hub - json', () => { 34 | const command = `package:installed:list -o ${session.hubOrg.username} --json`; 35 | const output = execCmd(command, { ensureExitCode: 0 }).jsonOutput?.result[0]; 36 | expect(output).to.have.keys( 37 | 'Id', 38 | 'SubscriberPackageId', 39 | 'SubscriberPackageName', 40 | 'SubscriberPackageNamespace', 41 | 'SubscriberPackageVersionId', 42 | 'SubscriberPackageVersionName', 43 | 'SubscriberPackageVersionNumber' 44 | ); 45 | expect(output?.Id).to.be.a('string'); 46 | expect(output?.SubscriberPackageId).to.be.a('string'); 47 | expect(output?.SubscriberPackageName).to.be.a('string'); 48 | expect(output?.SubscriberPackageNamespace).to.be.a('string'); 49 | expect(output?.SubscriberPackageVersionId).to.be.a('string'); 50 | expect(output?.SubscriberPackageVersionName).to.be.a('string'); 51 | expect(output?.SubscriberPackageVersionNumber).to.be.a('string'); 52 | }); 53 | }); 54 | -------------------------------------------------------------------------------- /test/commands/package/packageList.nut.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { execCmd, TestSession } from '@salesforce/cli-plugins-testkit'; 9 | import { expect, config } from 'chai'; 10 | import { Org } from '@salesforce/core'; 11 | import { Package } from '@salesforce/packaging'; 12 | 13 | config.truncateThreshold = 50_000; 14 | 15 | describe('package list', () => { 16 | let session: TestSession; 17 | let hubOrg: Org; 18 | let apiVersion: number; 19 | before(async () => { 20 | session = await TestSession.create({ 21 | devhubAuthStrategy: 'AUTO', 22 | }); 23 | hubOrg = await Org.create({ aliasOrUsername: session.hubOrg.username }); 24 | apiVersion = parseInt(hubOrg.getConnection().getApiVersion(), 10); 25 | }); 26 | 27 | after(async () => { 28 | await session?.clean(); 29 | }); 30 | it('should list packages in dev hub - json results', async () => { 31 | const packages = await Package.list(hubOrg.getConnection()); 32 | const command = `package:list -v ${session.hubOrg.username} --json`; 33 | const output = execCmd<{ [key: string]: unknown }>(command, { ensureExitCode: 0 }).jsonOutput; 34 | const keys = [ 35 | 'Id', 36 | 'SubscriberPackageId', 37 | 'Name', 38 | 'Description', 39 | 'NamespacePrefix', 40 | 'ContainerOptions', 41 | 'ConvertedFromPackageId', 42 | 'PackageErrorUsername', 43 | 'Alias', 44 | 'AppAnalyticsEnabled', 45 | 'CreatedBy', 46 | 'IsOrgDependent', 47 | ]; 48 | if (apiVersion < 59) { 49 | keys.splice(keys.indexOf('AppAnalyticsEnabled'), 1); 50 | } 51 | const deprecatedPackages = packages.filter((pkg) => pkg.IsDeprecated); 52 | const notDeprecatedCount = packages.length - deprecatedPackages.length; 53 | expect(output).to.be.ok; 54 | expect(output?.status).to.equal(0); 55 | expect(output?.result.length).to.have.within(notDeprecatedCount - 5, notDeprecatedCount + 5); 56 | expect(output?.result[0]).to.have.keys(keys); 57 | }); 58 | it('should list packages in dev hub - human readable results', () => { 59 | const command = `package:list -v ${session.hubOrg.username}`; 60 | const output = execCmd(command, { ensureExitCode: 0 }).shellOutput.stdout; 61 | expect(output).to.contain('Packages'); 62 | expect(output).to.match(/Namespace Prefix\s+?|Name\s+?|Id\s+?|Alias\s+?|Description\s+?|Type/); 63 | }); 64 | it('should list packages in dev hub - verbose human readable results', () => { 65 | const command = `package:list -v ${session.hubOrg.username} --verbose`; 66 | const output = execCmd(command, { ensureExitCode: 0 }).shellOutput.stdout; 67 | expect(output).to.contain('Packages'); 68 | let headerExpression = 69 | 'Namespace Prefix\\s+?|Name\\s+?|Id\\s+?|Alias\\s+?|Description\\s+?|Type\\s+?|Subscriber Package Id\\s+?|Converted From Package Id\\s+?|Org-Dependent Unlocked Package\\s+?|Error Notification Username\\s+?|Created By\\s+?|App Analytics Enabled'; 70 | if (apiVersion < 59.0) { 71 | headerExpression = headerExpression.replace('App Analytics Enabled\\s+?|', ''); 72 | } 73 | expect(output).to.match(new RegExp(headerExpression)); 74 | }); 75 | }); 76 | -------------------------------------------------------------------------------- /test/commands/package/packagePushUpgradeAbort.test.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2024, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { Config } from '@oclif/core'; 9 | import { TestContext, MockTestOrgData } from '@salesforce/core/testSetup'; 10 | import { expect } from 'chai'; 11 | import { PackagePushUpgrade } from '@salesforce/packaging'; 12 | import { SfCommand } from '@salesforce/sf-plugins-core'; 13 | import { PackagePushUpgradeAbortCommand } from '../../../src/commands/package/push-upgrade/abort.js'; 14 | 15 | describe('PackagePushUpgradeAbortCommand', () => { 16 | const $$ = new TestContext(); 17 | const testOrg = new MockTestOrgData(); 18 | let logStub: sinon.SinonStub; 19 | let abortStub: sinon.SinonStub; 20 | const config = new Config({ root: import.meta.url }); 21 | 22 | beforeEach(async () => { 23 | await $$.stubAuths(testOrg); 24 | await config.load(); 25 | 26 | logStub = $$.SANDBOX.stub(SfCommand.prototype, 'log'); 27 | 28 | abortStub = $$.SANDBOX.stub(PackagePushUpgrade, 'abort'); 29 | }); 30 | 31 | afterEach(() => { 32 | $$.restore(); 33 | }); 34 | 35 | it('should pass the right parameters to the library', async () => { 36 | const pushRequestId = '0DVxx0000004CCG'; 37 | const cmd = new PackagePushUpgradeAbortCommand(['-i', pushRequestId, '-v', testOrg.username], config); 38 | 39 | abortStub.resolves(true); 40 | const res = await cmd.run(); 41 | 42 | expect(res.success).to.be.true; 43 | // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access 44 | expect(abortStub.calledOnce).to.be.true; 45 | // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access 46 | expect(logStub.callCount).to.equal(1); 47 | // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access 48 | expect(logStub.args[0]).to.deep.equal([`Scheduled push upgrade ID [${pushRequestId}] was cancelled.`]); 49 | }); 50 | 51 | it('should throw an error if push-request-id is missing', async () => { 52 | const cmd = new PackagePushUpgradeAbortCommand(['-v', 'test@hub.org'], config); 53 | try { 54 | await cmd.run(); 55 | } catch (err) { 56 | const error = err as Error; 57 | expect(error.name).to.equal('Error'); 58 | expect(error.message).to.include('Missing required flag push-request-id'); 59 | } 60 | }); 61 | 62 | it('should throw an error if push-request status is not "Created" or "Pending" or is missing', async () => { 63 | abortStub.rejects(new Error('Abortion is only allowed for "Created" or "Pending" statuses.')); 64 | const cmd = new PackagePushUpgradeAbortCommand(['-i', '0DVxx0000004CCG', '-v', 'test@hub.org'], config); 65 | 66 | try { 67 | await cmd.run(); 68 | } catch (err) { 69 | const error = err as Error; 70 | const msg = 'Abortion is only allowed for "Created" or "Pending" statuses.'; 71 | expect(error.name).to.equal('Error'); 72 | expect(error.message).to.include(msg); 73 | } 74 | }); 75 | }); 76 | -------------------------------------------------------------------------------- /test/commands/package/packagePushUpgradeList.test.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2024, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | import { Config } from '@oclif/core'; 8 | import { TestContext, MockTestOrgData } from '@salesforce/core/testSetup'; 9 | import * as sinon from 'sinon'; 10 | import { expect } from 'chai'; 11 | import { env } from '@salesforce/kit'; 12 | import { PackagePushUpgrade, PackagePushRequestListResult } from '@salesforce/packaging'; 13 | import { stubSfCommandUx } from '@salesforce/sf-plugins-core'; 14 | import { PackagePushRequestListCommand } from '../../../src/commands/package/push-upgrade/list.js'; 15 | 16 | const pushUpgradeListSuccess: PackagePushRequestListResult[] = [ 17 | { 18 | Id: '0Af0M000000AxuqSAC', 19 | PackageVersionId: '04t0M000000AxuqSAC', 20 | PackageVersion: { 21 | Name: 'VersionName', 22 | MajorVersion: '1', 23 | MinorVersion: '1', 24 | }, 25 | Status: 'Success', 26 | ScheduledStartTime: '2024-01-02T00:00:00.000Z', 27 | StartTime: '2024-01-02T00:01:00.000Z', 28 | EndTime: '2024-01-02T00:10:00.000Z', 29 | OrgsScheduled: 2, 30 | OrgsUpgradeFailed: 0, 31 | OrgsUpgradeSucceeded: 2, 32 | }, 33 | ]; 34 | 35 | describe('package:pushupgrade:list - tests', () => { 36 | const $$ = new TestContext(); 37 | const testOrg = new MockTestOrgData(); 38 | let sfCommandStubs: ReturnType; 39 | let listStub: sinon.SinonStub; 40 | let getTotalJobsStub: sinon.SinonStub; 41 | let getFailedJobsStub: sinon.SinonStub; 42 | let getSucceededJobsStub: sinon.SinonStub; 43 | const config = new Config({ root: import.meta.url }); 44 | 45 | beforeEach(async () => { 46 | await $$.stubAuths(testOrg); 47 | await config.load(); 48 | sfCommandStubs = stubSfCommandUx($$.SANDBOX); 49 | 50 | listStub = $$.SANDBOX.stub(PackagePushUpgrade, 'list'); 51 | 52 | getTotalJobsStub = $$.SANDBOX.stub(PackagePushUpgrade, 'getTotalJobs'); 53 | 54 | getFailedJobsStub = $$.SANDBOX.stub(PackagePushUpgrade, 'getFailedJobs'); 55 | 56 | getSucceededJobsStub = $$.SANDBOX.stub(PackagePushUpgrade, 'getSucceededJobs'); 57 | }); 58 | 59 | afterEach(() => { 60 | $$.restore(); 61 | }); 62 | 63 | it('should list the push upgrade requests', async () => { 64 | const packageId = 'dummyPackageId'; 65 | const cmd = new PackagePushRequestListCommand(['-v', testOrg.username, '--package', packageId], config); 66 | 67 | listStub.resolves(pushUpgradeListSuccess); 68 | 69 | getTotalJobsStub.resolves(3); 70 | 71 | getFailedJobsStub.resolves(1); 72 | 73 | getSucceededJobsStub.resolves(2); 74 | 75 | const envSpy = $$.SANDBOX.spy(env, 'setBoolean').withArgs('SF_APPLY_REPLACEMENTS_ON_CONVERT', true); 76 | 77 | await cmd.run(); 78 | 79 | expect(envSpy.calledOnce).to.equal(false); 80 | // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access 81 | expect(sfCommandStubs.table.calledOnce).to.be.true; 82 | // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access 83 | expect(sfCommandStubs.warn.calledOnce).to.be.false; 84 | }); 85 | 86 | it('should handle no results found', async () => { 87 | const packageId = 'dummyPackageId'; 88 | const cmd = new PackagePushRequestListCommand(['-v', testOrg.username, '--package', packageId], config); 89 | 90 | listStub.resolves([]); 91 | 92 | await cmd.run(); 93 | 94 | // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access 95 | expect(sfCommandStubs.warn.calledOnce).to.be.true; 96 | }); 97 | 98 | it('should filter by is-migration flag', async () => { 99 | const packageId = '033XXXXXXXXXXXXXXX'; 100 | const cmdArgs = ['--target-dev-hub', testOrg.username, '--package', packageId, '--show-push-migrations-only']; 101 | const cmd = new PackagePushRequestListCommand(cmdArgs, config); 102 | 103 | listStub.resolves(pushUpgradeListSuccess); 104 | getTotalJobsStub.resolves(2); 105 | getFailedJobsStub.resolves(0); 106 | getSucceededJobsStub.resolves(2); 107 | 108 | await cmd.run(); 109 | 110 | expect(listStub.calledOnce).to.be.true; 111 | 112 | const listArgs = listStub.firstCall.args; 113 | expect(listArgs[1]).to.deep.include({ 114 | packageId, 115 | isMigration: true, 116 | status: undefined, 117 | scheduledLastDays: undefined, 118 | }); 119 | 120 | expect(sfCommandStubs.table.calledOnce).to.be.true; 121 | expect(sfCommandStubs.warn.calledOnce).to.be.false; 122 | }); 123 | }); 124 | -------------------------------------------------------------------------------- /test/commands/package/packagePushUpgradeReport.test.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2024, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | import { Config } from '@oclif/core'; 8 | import { TestContext } from '@salesforce/core/testSetup'; 9 | import { expect } from 'chai'; 10 | import { PackagePushUpgrade, PackagePushRequestReportResult } from '@salesforce/packaging'; 11 | import { stubSfCommandUx } from '@salesforce/sf-plugins-core'; 12 | import { PackagePushUpgradeReportCommand } from '../../../src/commands/package/push-upgrade/report.js'; 13 | 14 | const pushUpgradeReportSuccess: PackagePushRequestReportResult[] = [ 15 | { 16 | PackageVersion: { 17 | MetadataPackage: { 18 | Name: 'PackageName', 19 | NamespacePrefix: 'Namespace', 20 | }, 21 | MetadataPackageId: '0330M000000Axuq', 22 | Name: 'VersionName', 23 | MajorVersion: '1', 24 | MinorVersion: '1', 25 | }, 26 | PackageVersionId: '04t0M000000AxuqSAC', 27 | Id: '0DVxx0000004CCG', 28 | Status: 'Created', 29 | DurationSeconds: 60, 30 | ScheduledStartTime: '2024-01-02T00:00:00.000Z', 31 | StartTime: '2024-01-02T00:01:00.000Z', 32 | EndTime: '2024-01-02T00:10:00.000Z', 33 | }, 34 | ]; 35 | 36 | describe('package:pushupgrade:report - tests', () => { 37 | const $$ = new TestContext(); 38 | let sfCommandStubs: ReturnType; 39 | let reportStub: sinon.SinonStub; 40 | let getTotalJobsStub: sinon.SinonStub; 41 | let getFailedJobsStub: sinon.SinonStub; 42 | let getSucceededJobsStub: sinon.SinonStub; 43 | let getJobFailureReasonsStub: sinon.SinonStub; 44 | const config = new Config({ root: import.meta.url }); 45 | 46 | beforeEach(async () => { 47 | await $$.stubAuths(); 48 | await config.load(); 49 | sfCommandStubs = stubSfCommandUx($$.SANDBOX); 50 | reportStub = $$.SANDBOX.stub(PackagePushUpgrade, 'report'); 51 | 52 | getTotalJobsStub = $$.SANDBOX.stub(PackagePushUpgrade, 'getTotalJobs'); 53 | 54 | getFailedJobsStub = $$.SANDBOX.stub(PackagePushUpgrade, 'getFailedJobs'); 55 | 56 | getSucceededJobsStub = $$.SANDBOX.stub(PackagePushUpgrade, 'getSucceededJobs'); 57 | 58 | getJobFailureReasonsStub = $$.SANDBOX.stub(PackagePushUpgrade, 'getJobFailureReasons'); 59 | }); 60 | 61 | afterEach(() => { 62 | $$.restore(); 63 | }); 64 | 65 | it('should report the push upgrade request', async () => { 66 | const cmd = new PackagePushUpgradeReportCommand(['-i', '0DVxx0000004EXTGA2', '-v', 'test@hub.org'], config); 67 | 68 | reportStub.resolves(pushUpgradeReportSuccess); 69 | 70 | getTotalJobsStub.resolves(3); 71 | 72 | getFailedJobsStub.resolves(1); 73 | 74 | getSucceededJobsStub.resolves(2); 75 | 76 | getJobFailureReasonsStub.resolves([]); 77 | 78 | await cmd.run(); 79 | 80 | // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access 81 | expect(sfCommandStubs.table.calledOnce).to.be.true; 82 | // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access 83 | expect(sfCommandStubs.warn.calledOnce).to.be.false; 84 | }); 85 | 86 | it('should handle no results found', async () => { 87 | const cmd = new PackagePushUpgradeReportCommand(['-i', '0DVxx0000004EXTGA2', '-v', 'test@hub.org'], config); 88 | 89 | reportStub.resolves([]); 90 | 91 | await cmd.run(); 92 | 93 | // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access 94 | expect(sfCommandStubs.warn.calledOnce).to.be.true; 95 | }); 96 | 97 | it('should handle errors during report', async () => { 98 | const cmd = new PackagePushUpgradeReportCommand(['-i', '0DVxx0000004EXTGA2', '-v', 'test@hub.org'], config); 99 | 100 | reportStub.rejects(new Error('Report error')); 101 | try { 102 | await cmd.run(); 103 | // If cmd.run() resolves, this line will be reached, and the test should fail. 104 | expect.fail('Expected cmd.run() to reject, but it resolved.'); 105 | } catch (err) { 106 | // Assert that an error was indeed thrown 107 | expect(err).to.be.an.instanceof(Error); 108 | // Assert the error message matches 109 | expect((err as Error).message).to.equal('Report error'); 110 | } 111 | }); 112 | }); 113 | -------------------------------------------------------------------------------- /test/commands/package/packagePushUpgradeSchedule.test.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2024, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | import { Config } from '@oclif/core'; 8 | import { TestContext, MockTestOrgData } from '@salesforce/core/testSetup'; 9 | import * as sinon from 'sinon'; 10 | import { expect } from 'chai'; 11 | import { PackagePushUpgrade, PackagePushScheduleResult } from '@salesforce/packaging'; 12 | import { stubSfCommandUx } from '@salesforce/sf-plugins-core'; 13 | import { PackagePushScheduleCommand } from '../../../src/commands/package/push-upgrade/schedule.js'; 14 | 15 | const pushReq: PackagePushScheduleResult = { 16 | PushRequestId: 'mockPushJobId', 17 | ScheduledStartTime: '2023-01-01T00:00:00Z', 18 | Status: 'Scheduled', 19 | }; 20 | 21 | describe('package:pushupgrade:schedule - tests', () => { 22 | const $$ = new TestContext(); 23 | const testOrg = new MockTestOrgData(); 24 | let sfCommandStubs: ReturnType; 25 | let scheduleStub: sinon.SinonStub; 26 | const config = new Config({ root: import.meta.url }); 27 | 28 | beforeEach(async () => { 29 | await $$.stubAuths(testOrg); 30 | await config.load(); 31 | sfCommandStubs = stubSfCommandUx($$.SANDBOX); 32 | 33 | scheduleStub = $$.SANDBOX.stub(PackagePushUpgrade, 'schedule'); 34 | }); 35 | 36 | afterEach(() => { 37 | $$.restore(); 38 | }); 39 | 40 | it('should schedule the push upgrade with org input', async () => { 41 | const cmdArgsOrg = [ 42 | '-p', 43 | '04tXXXXXXXXXXXXXXX', 44 | '-v', 45 | testOrg.username, 46 | '--start-time', 47 | '2023-01-01T00:00:00Z', 48 | '--org-list', 49 | '00Dxx0000001gEREAY,00Dxx0000001gFAEA0', 50 | ]; 51 | const cmd = new PackagePushScheduleCommand(cmdArgsOrg, config); 52 | 53 | scheduleStub.resolves(pushReq); 54 | await cmd.run(); 55 | 56 | // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access 57 | expect(sfCommandStubs.log.calledOnce).to.be.true; 58 | // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access 59 | expect(scheduleStub.calledOnce).to.be.true; 60 | }); 61 | 62 | it('should schedule the push migration with --migrate-to-2gp flag', async () => { 63 | const packageId = '04tXXXXXXXXXXXXXXX'; 64 | const startTime = '2024-01-01T00:00:00Z'; 65 | const orgList = ['00Dxx0000001gEREAY', '00Dxx0000001gFAEA0']; 66 | const cmdArgs = [ 67 | '--package', 68 | packageId, 69 | '--target-dev-hub', 70 | testOrg.username, 71 | '--start-time', 72 | startTime, 73 | '--org-list', 74 | orgList.join(','), 75 | '--migrate-to-2gp', // Add the migration flag 76 | ]; 77 | const cmd = new PackagePushScheduleCommand(cmdArgs, config); 78 | 79 | scheduleStub.resolves(pushReq); 80 | const result = await cmd.run(); 81 | expect(result).to.deep.equal(pushReq); 82 | 83 | // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access 84 | expect(sfCommandStubs.log.calledOnce).to.be.true; 85 | expect(scheduleStub.calledOnce).to.be.true; 86 | 87 | // Verify the arguments passed to the schedule function 88 | const scheduleArgs = scheduleStub.firstCall.args; 89 | expect(scheduleArgs[1]).to.equal(packageId); // 2nd arg: packageId 90 | expect(scheduleArgs[2]).to.equal(startTime); // 3rd arg: startTime 91 | expect(scheduleArgs[3]).to.deep.equal(orgList); // 4th arg: orgList 92 | expect(scheduleArgs[4]).to.equal(true); // 5th arg: isMigration 93 | }); 94 | }); 95 | -------------------------------------------------------------------------------- /test/commands/package/packageUninstall.test.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2020, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | import os from 'node:os'; 8 | import { MockTestOrgData, TestContext } from '@salesforce/core/testSetup'; 9 | import { Config } from '@oclif/core'; 10 | import { assert, expect } from 'chai'; 11 | import sinon from 'sinon'; 12 | import { SfCommand } from '@salesforce/sf-plugins-core'; 13 | import { SubscriberPackageVersion } from '@salesforce/packaging'; 14 | import { PackageUninstallCommand } from '../../../src/commands/package/uninstall.js'; 15 | 16 | describe('package:uninstall', () => { 17 | const $$ = new TestContext(); 18 | const testOrg = new MockTestOrgData(); 19 | const config = new Config({ root: import.meta.url }); 20 | 21 | // stubs 22 | let logStub: sinon.SinonStub; 23 | 24 | before(async () => { 25 | await $$.stubAuths(testOrg); 26 | await config.load(); 27 | }); 28 | 29 | beforeEach(async () => { 30 | logStub = $$.SANDBOX.stub(SfCommand.prototype, 'log'); 31 | }); 32 | 33 | afterEach(() => { 34 | $$.restore(); 35 | $$.SANDBOX.restore(); 36 | }); 37 | 38 | const libraryStubResult = (status: 'Error' | 'InProgress' | 'Queued' | 'Success'): void => { 39 | $$.SANDBOX.stub(SubscriberPackageVersion.prototype, 'uninstall').resolves({ 40 | Id: '06y23000000002MXXX', 41 | IsDeleted: true, 42 | CreatedDate: 123, 43 | CreatedById: 'user', 44 | LastModifiedDate: 123, 45 | LastModifiedById: '', 46 | SystemModstamp: 123, 47 | SubscriberPackageVersionId: '04t4p000002BaHYXXX', 48 | Status: status, 49 | }); 50 | }; 51 | 52 | it('should print Success status correctly', async () => { 53 | libraryStubResult('Success'); 54 | const result = await new PackageUninstallCommand( 55 | ['--package', '04t4p000002BaHYXXX', '-o', testOrg.username], 56 | config 57 | ).run(); 58 | expect(result.Status).to.equal('Success'); 59 | expect(logStub.callCount).to.equal(1); 60 | expect(logStub.firstCall.args[0]).to.equal('Successfully uninstalled package [04t4p000002BaHYXXX]'); 61 | }); 62 | 63 | it('should print InProgress status correctly', async () => { 64 | libraryStubResult('InProgress'); 65 | const result = await new PackageUninstallCommand( 66 | ['--package', '04t4p000002BaHYXXX', '-o', testOrg.username], 67 | config 68 | ).run(); 69 | expect(result.Status).to.equal('InProgress'); 70 | expect(logStub.callCount).to.equal(1); 71 | expect(logStub.firstCall.args[0]).to.deep.equal( 72 | `PackageUninstallRequest is currently InProgress.${os.EOL}You can continue to query the status using sf package uninstall report -i 06y23000000002MXXX -o ${testOrg.username}` 73 | ); 74 | }); 75 | 76 | it('should validate --package', async () => { 77 | libraryStubResult('Success'); 78 | const result = await new PackageUninstallCommand( 79 | ['--package', '04t4p000002BaHYXXX', '-o', testOrg.username], 80 | config 81 | ).run(); 82 | expect(result.Status).to.equal('Success'); 83 | expect(logStub.callCount).to.equal(1); 84 | expect(logStub.firstCall.args[0]).to.equal('Successfully uninstalled package [04t4p000002BaHYXXX]'); 85 | }); 86 | 87 | it("should validate --package (doesn't start with 04t)", async () => { 88 | try { 89 | await new PackageUninstallCommand(['--package', '03t4p000002BaHYXXX', '-o', testOrg.username], config).run(); 90 | assert.fail('the above should throw an invalid version error'); 91 | } catch (e) { 92 | expect((e as Error).message).to.include( 93 | 'Invalid alias or ID: 03t4p000002BaHYXXX. Either your alias is invalid or undefined, or the ID (04t) provided is invalid.' 94 | ); 95 | } 96 | }); 97 | }); 98 | -------------------------------------------------------------------------------- /test/commands/package/packageVersionRetrieve.test.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2020, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | import { join } from 'node:path'; 8 | import { MockTestOrgData, TestContext } from '@salesforce/core/testSetup'; 9 | import { Config } from '@oclif/core'; 10 | import { expect } from 'chai'; 11 | import { SourceComponent, registry } from '@salesforce/source-deploy-retrieve'; 12 | import { Package, PackageVersionMetadataDownloadResult } from '@salesforce/packaging'; 13 | import { PackageVersionRetrieveCommand } from '../../../src/commands/package/version/retrieve.js'; 14 | 15 | const myPackageVersion04t = '04t000000000001'; 16 | 17 | const pkgVersionRetrieveSuccessResult: PackageVersionMetadataDownloadResult = { 18 | packagePath: '/tmp/foo', 19 | converted: [ 20 | new SourceComponent({ 21 | name: 'ComponentA', 22 | type: registry.types['apexclass'], 23 | xml: join('nonexistentDir', 'ComponentA.cls-meta.xml'), 24 | content: join('nonexistentDir', 'ComponentA.cls'), 25 | }), 26 | new SourceComponent({ 27 | name: 'ComponentB', 28 | type: registry.types['customobject'], 29 | content: join('nonexistentDir', 'ComponentB.object-meta.xml'), 30 | }), 31 | ], 32 | }; 33 | 34 | const expectedRetrievedComponents = [ 35 | { 36 | filePath: join('nonexistentDir', 'ComponentA.cls-meta.xml'), 37 | fullName: 'ComponentA', 38 | type: 'ApexClass', 39 | }, 40 | { 41 | filePath: join('nonexistentDir', 'ComponentA.cls'), 42 | fullName: 'ComponentA', 43 | type: 'ApexClass', 44 | }, 45 | { 46 | filePath: join('nonexistentDir', 'ComponentB.object-meta.xml'), 47 | fullName: 'ComponentB', 48 | type: 'CustomObject', 49 | }, 50 | ]; 51 | 52 | describe('package:version:retrieve - tests', () => { 53 | const $$ = new TestContext(); 54 | const testOrg = new MockTestOrgData(); 55 | const downloadStub = $$.SANDBOX.stub(Package, 'downloadPackageVersionMetadata'); 56 | const config = new Config({ root: import.meta.url }); 57 | 58 | before(async () => { 59 | await $$.stubAuths(testOrg); 60 | await config.load(); 61 | }); 62 | 63 | afterEach(() => { 64 | $$.restore(); 65 | }); 66 | 67 | describe('package:version:retrieve', () => { 68 | it('should display retrieved files', async () => { 69 | downloadStub.resolves(pkgVersionRetrieveSuccessResult); 70 | const cmd = new PackageVersionRetrieveCommand(['-p', myPackageVersion04t, '-o', 'test@dev.org'], config); 71 | const res = await cmd.run(); 72 | expect(res).to.deep.equal(expectedRetrievedComponents); 73 | }); 74 | }); 75 | }); 76 | -------------------------------------------------------------------------------- /test/commands/package/version.delete.test.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2020, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | import { MockTestOrgData, TestContext } from '@salesforce/core/testSetup'; 8 | import { Config } from '@oclif/core'; 9 | import { expect } from 'chai'; 10 | import { PackageSaveResult, PackageVersion } from '@salesforce/packaging'; 11 | import sinon from 'sinon'; 12 | import { SfCommand } from '@salesforce/sf-plugins-core'; 13 | import { SfProject } from '@salesforce/core'; 14 | import { PackageVersionDeleteCommand } from '../../../src/commands/package/version/delete.js'; 15 | 16 | describe('package:version:delete', () => { 17 | const $$ = new TestContext(); 18 | const testOrg = new MockTestOrgData(); 19 | const config = new Config({ root: import.meta.url }); 20 | 21 | // stubs 22 | let uxSuccessStub: sinon.SinonStub; 23 | let uxConfirmStub: sinon.SinonStub; 24 | 25 | let packageVersionStub: sinon.SinonStub; 26 | let deleteStub: sinon.SinonStub; 27 | let undeleteStub: sinon.SinonStub; 28 | 29 | beforeEach(async () => { 30 | uxSuccessStub = $$.SANDBOX.stub(SfCommand.prototype, 'logSuccess'); 31 | uxConfirmStub = $$.SANDBOX.stub(SfCommand.prototype, 'confirm'); 32 | deleteStub = $$.SANDBOX.stub(); 33 | undeleteStub = $$.SANDBOX.stub(); 34 | 35 | // The PackageVersion class is tested in the packaging library, so 36 | // we just stub the public APIs used by the command. 37 | packageVersionStub = $$.SANDBOX.stub().callsFake(() => ({ 38 | delete: deleteStub, 39 | undelete: undeleteStub, 40 | })); 41 | Object.setPrototypeOf(PackageVersion, packageVersionStub); 42 | }); 43 | 44 | before(async () => { 45 | await $$.stubAuths(testOrg); 46 | await config.load(); 47 | }); 48 | 49 | afterEach(() => { 50 | $$.restore(); 51 | $$.SANDBOX.restore(); 52 | }); 53 | 54 | beforeEach(() => {}); 55 | 56 | it('should error without required --package param', async () => { 57 | try { 58 | await new PackageVersionDeleteCommand(['-v', testOrg.username], config).run(); 59 | expect(false, 'Expected required flag error').to.be.true; 60 | } catch (err) { 61 | const error = err as Error; 62 | expect(error.name).to.equal('Error'); 63 | expect(error.message).to.include('Missing required flag package'); 64 | } 65 | }); 66 | 67 | it('should error pkg version alias not found in project', async () => { 68 | try { 69 | const command = new PackageVersionDeleteCommand(['-p', 'subscriberPV-alias', '-v', 'foor@bar.org'], config); 70 | command.project = SfProject.getInstance(); 71 | uxConfirmStub.resolves(true); 72 | await command.run(); 73 | 74 | expect(false, 'Expected invalid id error').to.be.true; 75 | } catch (err) { 76 | const error = err as Error; 77 | expect(error.name).to.equal('PackageAliasNotFoundError'); 78 | } 79 | }); 80 | it('should delete a package version', async () => { 81 | deleteStub.reset(); 82 | deleteStub = $$.SANDBOX.stub(PackageVersion.prototype, 'delete').resolves({ 83 | errors: [], 84 | id: 'testId', 85 | success: true, 86 | } as PackageSaveResult); 87 | uxConfirmStub.resolves(true); 88 | 89 | const command = new PackageVersionDeleteCommand(['-p', '04t6A000002zgKSQAY', '-v', 'foor@bar.org'], config); 90 | command.project = SfProject.getInstance(); 91 | const results: PackageSaveResult = await command.run(); 92 | expect(results.id).to.equal('testId'); 93 | expect(uxSuccessStub.calledOnce).to.be.true; 94 | expect(uxSuccessStub.args[0][0]).to.equal('Successfully deleted the package version with ID: testId'); 95 | expect(results.id).to.equal('testId'); 96 | }); 97 | it('should undelete a package version', async () => { 98 | deleteStub.reset(); 99 | deleteStub = $$.SANDBOX.stub(PackageVersion.prototype, 'undelete').resolves({ 100 | errors: [], 101 | id: 'testId', 102 | success: true, 103 | } as PackageSaveResult); 104 | uxConfirmStub.resolves(true); 105 | const command = new PackageVersionDeleteCommand( 106 | ['-p', '04t6A000002zgKSQAY', '-v', 'foor@bar.org', '--undelete'], 107 | config 108 | ); 109 | command.project = SfProject.getInstance(); 110 | const results: PackageSaveResult = await command.run(); 111 | expect(uxSuccessStub.calledOnce).to.be.true; 112 | expect(uxSuccessStub.args[0][0]).to.equal('Successfully undeleted package version testId.'); 113 | expect(results.id).to.equal('testId'); 114 | }); 115 | }); 116 | -------------------------------------------------------------------------------- /test/commands/package1/versionDisplay.nut.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { execCmd, TestSession } from '@salesforce/cli-plugins-testkit'; 9 | import { expect } from 'chai'; 10 | import { Package1Display } from '@salesforce/packaging'; 11 | 12 | describe('package1:version:display', () => { 13 | let session: TestSession; 14 | // TODO: na40 required as DevHub 15 | // hardcoded for now, eventually will be able to query from the org with package1:version:list 16 | const packageVersionId = '04t46000001ZfaAAAS'; 17 | before(async () => { 18 | session = await TestSession.create({ 19 | devhubAuthStrategy: 'AUTO', 20 | project: { name: 'package1VersionDisplay' }, 21 | }); 22 | }); 23 | 24 | after(async () => { 25 | await session?.clean(); 26 | }); 27 | 28 | it('should list 1gp packages in dev hub - human readable results', () => { 29 | const command = `package1:version:display -i ${packageVersionId} -o ${session.hubOrg.username}`; 30 | const output = execCmd(command, { ensureExitCode: 0 }).shellOutput.stdout; 31 | expect(output).to.match( 32 | /MetadataPackageVersionId\s+?|MetadataPackageId\s+?|Name\s+?|Version\s+?|ReleaseState\s+?|BuildNumber/ 33 | ); 34 | }); 35 | 36 | it('should list 1gp packages in dev hub - human readable results - no results', () => { 37 | // fake package ID 38 | const command = `package1:version:display -i 04t46000001ZfaXXXX -o ${session.hubOrg.username}`; 39 | const output = execCmd(command, { ensureExitCode: 0 }).shellOutput; 40 | expect(output.stderr).to.contain('No results found'); 41 | }); 42 | 43 | it('should validate packageversionid flag (too short)', () => { 44 | // fake package ID - too short 45 | const command = `package1:version:display -i 04t46000001Zfa -o ${session.hubOrg.username}`; 46 | const output = execCmd(command, { ensureExitCode: 'nonZero' }).shellOutput.stderr; 47 | expect(output).to.contain('The id must be 15 or 18 characters.'); 48 | }); 49 | 50 | it("should validate packageversionid flag (doesn't start with 04t)", () => { 51 | // fake package ID - not an 04t package 52 | const command = `package1:version:display -i 05t46000001ZfaAAAS -o ${session.hubOrg.username}`; 53 | const output = execCmd(command, { ensureExitCode: 'nonZero' }).shellOutput.stderr; 54 | expect(output).to.contain('The id must begin with 04t'); 55 | }); 56 | 57 | it('should list 1gp packages in dev hub - json', () => { 58 | const command = `package1:version:display -i ${packageVersionId} -o ${session.hubOrg.username} --json`; 59 | const output = execCmd(command, { ensureExitCode: 0 }).jsonOutput?.result[0]; 60 | expect(output).to.have.keys( 61 | 'MetadataPackageVersionId', 62 | 'MetadataPackageId', 63 | 'Name', 64 | 'Version', 65 | 'ReleaseState', 66 | 'BuildNumber' 67 | ); 68 | expect(output?.BuildNumber).to.be.a('number'); 69 | expect(output?.ReleaseState).to.be.a('string'); 70 | expect(output?.MetadataPackageVersionId).to.be.a('string'); 71 | expect(output?.MetadataPackageId).to.be.a('string'); 72 | expect(output?.Version).to.be.a('string'); 73 | }); 74 | }); 75 | -------------------------------------------------------------------------------- /test/commands/package1/versionList.nut.ts: -------------------------------------------------------------------------------- 1 | /* 2 | * Copyright (c) 2022, salesforce.com, inc. 3 | * All rights reserved. 4 | * Licensed under the BSD 3-Clause license. 5 | * For full license text, see LICENSE.txt file in the repo root or https://opensource.org/licenses/BSD-3-Clause 6 | */ 7 | 8 | import { execCmd, TestSession } from '@salesforce/cli-plugins-testkit'; 9 | import { expect } from 'chai'; 10 | import { Package1Display } from '@salesforce/packaging'; 11 | 12 | describe('package1:version:list', () => { 13 | let session: TestSession; 14 | let packageId: string | undefined; 15 | 16 | // TODO: na40 required as DevHub 17 | before(async () => { 18 | session = await TestSession.create({ 19 | devhubAuthStrategy: 'AUTO', 20 | project: { name: 'package1VersionList' }, 21 | }); 22 | }); 23 | 24 | after(async () => { 25 | await session?.clean(); 26 | }); 27 | 28 | it('should list all 1gp packages in dev hub - human readable results', () => { 29 | const command = `package1:version:list -o ${session.hubOrg.username}`; 30 | const output = execCmd(command, { ensureExitCode: 0 }).shellOutput.stdout; 31 | expect(output).to.match( 32 | /MetadataPackageVersionId\s+?|MetadataPackageId\s+?|Name\s+?|Version\s+?|ReleaseState\s+?|BuildNumber/ 33 | ); 34 | }); 35 | 36 | it('should list 1gp packages in dev hub - json', () => { 37 | const command = `package1:version:list -o ${session.hubOrg.username} --json`; 38 | const output = execCmd(command, { ensureExitCode: 0 }).jsonOutput?.result[0]; 39 | expect(output).to.have.keys( 40 | 'MetadataPackageVersionId', 41 | 'MetadataPackageId', 42 | 'Name', 43 | 'Version', 44 | 'ReleaseState', 45 | 'BuildNumber' 46 | ); 47 | expect(output?.BuildNumber).to.be.a('number'); 48 | expect(output?.ReleaseState).to.be.a('string'); 49 | expect(output?.MetadataPackageVersionId).to.be.a('string'); 50 | expect(output?.MetadataPackageId).to.be.a('string'); 51 | expect(output?.Version).to.be.a('string'); 52 | }); 53 | 54 | before(() => { 55 | const command = `package1:version:list -o ${session.hubOrg.username} --json`; 56 | packageId = execCmd(command, { ensureExitCode: 0 }).jsonOutput?.result[0].MetadataPackageId; 57 | }); 58 | 59 | it('should list all 1gp related to the package id - human readable results', () => { 60 | const command = `package1:version:list -i ${packageId} -o ${session.hubOrg.username}`; 61 | const output = execCmd(command, { ensureExitCode: 0 }).shellOutput.stdout; 62 | expect(output).to.match( 63 | /MetadataPackageVersionId\s+?|MetadataPackageId\s+?|Name\s+?|Version\s+?|ReleaseState\s+?|BuildNumber/ 64 | ); 65 | }); 66 | 67 | it('should list 1gp packages in dev hub related to the package id - human readable results - no results', () => { 68 | // fake package ID 69 | const command = `package1:version:list -i 03346000000MrC0AXX -o ${session.hubOrg.username}`; 70 | const output = execCmd(command, { ensureExitCode: 0 }).shellOutput; 71 | expect(output?.stderr?.trim()).to.contain('No Results Found'); 72 | }); 73 | 74 | it("should validate packageversionid flag (doesn't start with 033)", () => { 75 | // fake package ID - not an 033 package 76 | const command = `package1:version:list -i 03446000001ZfaAAAS -o ${session.hubOrg.username}`; 77 | const output = execCmd(command, { ensureExitCode: 'nonZero' }).shellOutput.stderr; 78 | expect(output).to.contain('The id must begin with 033.'); 79 | }); 80 | 81 | it('should validate packageversionid flag (too short)', () => { 82 | // fake package ID - not an 033 package 83 | const command = `package1:version:list -i 03346000001Zfa -o ${session.hubOrg.username}`; 84 | const output = execCmd(command, { ensureExitCode: 'nonZero' }).shellOutput.stderr; 85 | expect(output).to.contain('The id must be 18 characters.'); 86 | }); 87 | 88 | it('should list 1gp packages in dev hub related to the package id - json', () => { 89 | const command = `package1:version:list -i ${packageId} -o ${session.hubOrg.username} --json`; 90 | const output = execCmd(command, { ensureExitCode: 0 }).jsonOutput?.result[0]; 91 | expect(output).to.have.keys( 92 | 'MetadataPackageVersionId', 93 | 'MetadataPackageId', 94 | 'Name', 95 | 'Version', 96 | 'ReleaseState', 97 | 'BuildNumber' 98 | ); 99 | expect(output?.BuildNumber).to.be.a('number'); 100 | expect(output?.ReleaseState).to.be.a('string'); 101 | expect(output?.MetadataPackageVersionId).to.be.a('string'); 102 | expect(output?.MetadataPackageId).to.be.a('string'); 103 | expect(output?.Version).to.be.a('string'); 104 | }); 105 | }); 106 | -------------------------------------------------------------------------------- /test/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "extends": "@salesforce/dev-config/tsconfig-test-strict-esm", 3 | "include": ["./**/*.ts"], 4 | "compilerOptions": { 5 | "skipLibCheck": true 6 | } 7 | } 8 | -------------------------------------------------------------------------------- /tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "extends": "@salesforce/dev-config/tsconfig-strict-esm", 3 | "compilerOptions": { 4 | "outDir": "lib", 5 | "rootDir": "src", 6 | "skipLibCheck": true 7 | }, 8 | "include": ["./src/**/*.ts"] 9 | } 10 | --------------------------------------------------------------------------------