@salesforce/plugin-data 3.6.9 → 3.7.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +130 -18
- package/lib/bulkDataRequestCache.js +81 -5
- package/lib/bulkDataRequestCache.js.map +1 -1
- package/lib/bulkUtils.js +94 -0
- package/lib/bulkUtils.js.map +1 -1
- package/lib/commands/data/export/bulk.js +213 -0
- package/lib/commands/data/export/bulk.js.map +1 -0
- package/lib/commands/data/export/resume.js +82 -0
- package/lib/commands/data/export/resume.js.map +1 -0
- package/lib/types.js.map +1 -1
- package/messages/data.export.bulk.md +67 -0
- package/messages/data.export.resume.md +25 -0
- package/messages/messages.md +5 -1
- package/oclif.manifest.json +260 -1
- package/package.json +11 -8
|
@@ -0,0 +1,213 @@
|
|
|
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 * as fs from 'node:fs';
|
|
8
|
+
import { platform } from 'node:os';
|
|
9
|
+
import { SfCommand, Flags } from '@salesforce/sf-plugins-core';
|
|
10
|
+
import { Messages, Org } from '@salesforce/core';
|
|
11
|
+
import { MultiStageOutput } from '@oclif/multi-stage-output';
|
|
12
|
+
import terminalLink from 'terminal-link';
|
|
13
|
+
import { QueryJobV2 } from '@jsforce/jsforce-node/lib/api/bulk2.js';
|
|
14
|
+
import { Duration } from '@salesforce/kit';
|
|
15
|
+
import { BulkExportRequestCache } from '../../../bulkDataRequestCache.js';
|
|
16
|
+
import { exportRecords } from '../../../bulkUtils.js';
|
|
17
|
+
Messages.importMessagesDirectoryFromMetaUrl(import.meta.url);
|
|
18
|
+
const messages = Messages.loadMessages('@salesforce/plugin-data', 'data.export.bulk');
|
|
19
|
+
export default class DataExportBulk extends SfCommand {
|
|
20
|
+
static summary = messages.getMessage('summary');
|
|
21
|
+
static description = messages.getMessage('description');
|
|
22
|
+
static examples = messages.getMessages('examples');
|
|
23
|
+
static flags = {
|
|
24
|
+
'target-org': Flags.requiredOrg(),
|
|
25
|
+
'api-version': Flags.orgApiVersion(),
|
|
26
|
+
wait: Flags.duration({
|
|
27
|
+
summary: messages.getMessage('flags.wait.summary'),
|
|
28
|
+
char: 'w',
|
|
29
|
+
helpValue: '<minutes>',
|
|
30
|
+
unit: 'minutes',
|
|
31
|
+
exclusive: ['async'],
|
|
32
|
+
}),
|
|
33
|
+
async: Flags.boolean({
|
|
34
|
+
summary: messages.getMessage('flags.async.summary'),
|
|
35
|
+
exclusive: ['wait'],
|
|
36
|
+
}),
|
|
37
|
+
query: Flags.string({
|
|
38
|
+
summary: messages.getMessage('flags.query.summary'),
|
|
39
|
+
char: 'q',
|
|
40
|
+
exclusive: ['query-file'],
|
|
41
|
+
}),
|
|
42
|
+
'query-file': Flags.file({
|
|
43
|
+
summary: messages.getMessage('flags.query-file.summary'),
|
|
44
|
+
exists: true,
|
|
45
|
+
exclusive: ['query'],
|
|
46
|
+
}),
|
|
47
|
+
'all-rows': Flags.boolean({
|
|
48
|
+
summary: messages.getMessage('flags.all-rows.summary'),
|
|
49
|
+
}),
|
|
50
|
+
'output-file': Flags.file({
|
|
51
|
+
summary: messages.getMessage('flags.output-file.summary'),
|
|
52
|
+
required: true,
|
|
53
|
+
}),
|
|
54
|
+
'result-format': Flags.option({
|
|
55
|
+
required: true,
|
|
56
|
+
options: ['csv', 'json'],
|
|
57
|
+
default: 'csv',
|
|
58
|
+
summary: messages.getMessage('flags.result-format.summary'),
|
|
59
|
+
char: 'r',
|
|
60
|
+
})(),
|
|
61
|
+
'column-delimiter': Flags.option({
|
|
62
|
+
options: ['BACKQUOTE', 'CARET', 'COMMA', 'PIPE', 'SEMICOLON', 'TAB'],
|
|
63
|
+
summary: messages.getMessage('flags.column-delimiter.summary'),
|
|
64
|
+
relationships: [
|
|
65
|
+
{
|
|
66
|
+
type: 'some',
|
|
67
|
+
flags: [
|
|
68
|
+
{
|
|
69
|
+
name: 'result-format',
|
|
70
|
+
// eslint-disable-next-line @typescript-eslint/require-await
|
|
71
|
+
when: async (flags) => flags['result-format'] === 'csv',
|
|
72
|
+
},
|
|
73
|
+
],
|
|
74
|
+
},
|
|
75
|
+
],
|
|
76
|
+
})(),
|
|
77
|
+
'line-ending': Flags.option({
|
|
78
|
+
summary: messages.getMessage('flags.line-ending.summary'),
|
|
79
|
+
options: ['LF', 'CRLF'],
|
|
80
|
+
relationships: [
|
|
81
|
+
{
|
|
82
|
+
type: 'some',
|
|
83
|
+
flags: [
|
|
84
|
+
{
|
|
85
|
+
name: 'result-format',
|
|
86
|
+
// eslint-disable-next-line @typescript-eslint/require-await
|
|
87
|
+
when: async (flags) => flags['result-format'] === 'csv',
|
|
88
|
+
},
|
|
89
|
+
],
|
|
90
|
+
},
|
|
91
|
+
],
|
|
92
|
+
})(),
|
|
93
|
+
};
|
|
94
|
+
async run() {
|
|
95
|
+
const { flags } = await this.parse(DataExportBulk);
|
|
96
|
+
const conn = flags['target-org'].getConnection(flags['api-version']);
|
|
97
|
+
const timeout = flags.async ? Duration.minutes(0) : flags.wait ?? Duration.minutes(0);
|
|
98
|
+
// `flags['query-file']` will be present if `flags.query` isn't. oclif's `exclusive` isn't quite that clever
|
|
99
|
+
const soqlQuery = flags.query ?? fs.readFileSync(flags['query-file'], 'utf8');
|
|
100
|
+
const lineEnding = flags['line-ending'] ?? platform() === 'win32' ? 'CRLF' : 'LF';
|
|
101
|
+
const columnDelimiter = flags['column-delimiter'] ?? 'COMMA';
|
|
102
|
+
const async = timeout.milliseconds === 0;
|
|
103
|
+
const baseUrl = flags['target-org'].getField(Org.Fields.INSTANCE_URL).toString();
|
|
104
|
+
const ms = new MultiStageOutput({
|
|
105
|
+
jsonEnabled: flags.json ?? false,
|
|
106
|
+
stages: async
|
|
107
|
+
? ['creating query job', 'done']
|
|
108
|
+
: ['creating query job', 'processing the job', 'exporting records'],
|
|
109
|
+
title: async ? 'Exporting data (async)' : 'Exporting data',
|
|
110
|
+
postStagesBlock: [
|
|
111
|
+
{
|
|
112
|
+
label: 'Status',
|
|
113
|
+
type: 'dynamic-key-value',
|
|
114
|
+
bold: true,
|
|
115
|
+
get: (data) => data?.state,
|
|
116
|
+
},
|
|
117
|
+
{
|
|
118
|
+
label: 'Job Id',
|
|
119
|
+
type: 'dynamic-key-value',
|
|
120
|
+
bold: true,
|
|
121
|
+
get: (data) => data?.id &&
|
|
122
|
+
terminalLink(data.id, `${baseUrl}/lightning/setup/AsyncApiJobStatus/page?address=${encodeURIComponent(`/${data.id}`)}`),
|
|
123
|
+
},
|
|
124
|
+
],
|
|
125
|
+
});
|
|
126
|
+
// async: create query job in the org but don't poll for its status
|
|
127
|
+
if (async) {
|
|
128
|
+
const job = new QueryJobV2(conn, {
|
|
129
|
+
bodyParams: {
|
|
130
|
+
query: soqlQuery,
|
|
131
|
+
operation: flags['all-rows'] ? 'queryAll' : 'query',
|
|
132
|
+
columnDelimiter,
|
|
133
|
+
lineEnding,
|
|
134
|
+
},
|
|
135
|
+
pollingOptions: {
|
|
136
|
+
pollTimeout: timeout.milliseconds,
|
|
137
|
+
pollInterval: 5000,
|
|
138
|
+
},
|
|
139
|
+
});
|
|
140
|
+
job.on('error', (err) => {
|
|
141
|
+
ms.stop('failed');
|
|
142
|
+
throw err;
|
|
143
|
+
});
|
|
144
|
+
job.on('open', (jobInfo) => {
|
|
145
|
+
ms.goto('done', { id: jobInfo.id });
|
|
146
|
+
ms.stop();
|
|
147
|
+
});
|
|
148
|
+
ms.goto('creating query job');
|
|
149
|
+
try {
|
|
150
|
+
const jobInfo = await job.open();
|
|
151
|
+
const cache = await BulkExportRequestCache.create();
|
|
152
|
+
await cache.createCacheEntryForRequest(jobInfo.id, {
|
|
153
|
+
filePath: flags['output-file'],
|
|
154
|
+
format: flags['result-format'],
|
|
155
|
+
columnDelimiter,
|
|
156
|
+
}, conn.getUsername(), conn.getApiVersion());
|
|
157
|
+
this.log(messages.getMessage('export.timeout', [jobInfo.id]));
|
|
158
|
+
return {
|
|
159
|
+
jobId: jobInfo.id,
|
|
160
|
+
filePath: flags['output-file'],
|
|
161
|
+
};
|
|
162
|
+
}
|
|
163
|
+
catch (err) {
|
|
164
|
+
ms.stop('failed');
|
|
165
|
+
throw err;
|
|
166
|
+
}
|
|
167
|
+
}
|
|
168
|
+
const queryJob = new QueryJobV2(conn, {
|
|
169
|
+
bodyParams: {
|
|
170
|
+
query: soqlQuery,
|
|
171
|
+
operation: flags['all-rows'] ? 'queryAll' : 'query',
|
|
172
|
+
columnDelimiter: flags['column-delimiter'],
|
|
173
|
+
lineEnding,
|
|
174
|
+
},
|
|
175
|
+
pollingOptions: {
|
|
176
|
+
pollTimeout: timeout.milliseconds,
|
|
177
|
+
pollInterval: 5000,
|
|
178
|
+
},
|
|
179
|
+
});
|
|
180
|
+
queryJob.on('error', () => {
|
|
181
|
+
ms.stop('failed');
|
|
182
|
+
});
|
|
183
|
+
queryJob.on('open', (jobInfo) => {
|
|
184
|
+
ms.goto('processing the job', {
|
|
185
|
+
state: jobInfo.state,
|
|
186
|
+
id: jobInfo.id,
|
|
187
|
+
});
|
|
188
|
+
});
|
|
189
|
+
ms.goto('creating query job');
|
|
190
|
+
queryJob.on('jobComplete', (jobInfo) => {
|
|
191
|
+
ms.goto('exporting records', { state: jobInfo.state });
|
|
192
|
+
});
|
|
193
|
+
await queryJob.open();
|
|
194
|
+
try {
|
|
195
|
+
const jobInfo = await exportRecords(conn, queryJob, {
|
|
196
|
+
filePath: flags['output-file'],
|
|
197
|
+
format: flags['result-format'],
|
|
198
|
+
columnDelimiter,
|
|
199
|
+
});
|
|
200
|
+
ms.stop();
|
|
201
|
+
this.log(`${jobInfo.numberRecordsProcessed} records written to ${flags['output-file']}`);
|
|
202
|
+
return {
|
|
203
|
+
totalSize: jobInfo.numberRecordsProcessed,
|
|
204
|
+
filePath: flags['output-file'],
|
|
205
|
+
};
|
|
206
|
+
}
|
|
207
|
+
catch (err) {
|
|
208
|
+
ms.stop('failed');
|
|
209
|
+
throw err;
|
|
210
|
+
}
|
|
211
|
+
}
|
|
212
|
+
}
|
|
213
|
+
//# sourceMappingURL=bulk.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"bulk.js","sourceRoot":"","sources":["../../../../src/commands/data/export/bulk.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,82 @@
|
|
|
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 { SfCommand, Flags } from '@salesforce/sf-plugins-core';
|
|
8
|
+
import { Messages } from '@salesforce/core';
|
|
9
|
+
import { QueryJobV2 } from '@jsforce/jsforce-node/lib/api/bulk2.js';
|
|
10
|
+
import { MultiStageOutput } from '@oclif/multi-stage-output';
|
|
11
|
+
import { BulkExportRequestCache } from '../../../bulkDataRequestCache.js';
|
|
12
|
+
import { exportRecords } from '../../../bulkUtils.js';
|
|
13
|
+
Messages.importMessagesDirectoryFromMetaUrl(import.meta.url);
|
|
14
|
+
const messages = Messages.loadMessages('@salesforce/plugin-data', 'data.export.resume');
|
|
15
|
+
export default class DataExportResume extends SfCommand {
|
|
16
|
+
static summary = messages.getMessage('summary');
|
|
17
|
+
static description = messages.getMessage('description');
|
|
18
|
+
static examples = messages.getMessages('examples');
|
|
19
|
+
static flags = {
|
|
20
|
+
'job-id': Flags.salesforceId({
|
|
21
|
+
length: 18,
|
|
22
|
+
char: 'i',
|
|
23
|
+
startsWith: '750',
|
|
24
|
+
summary: messages.getMessage('flags.job-id.summary'),
|
|
25
|
+
exactlyOne: ['job-id', 'use-most-recent'],
|
|
26
|
+
}),
|
|
27
|
+
'use-most-recent': Flags.boolean({
|
|
28
|
+
summary: messages.getMessage('flags.use-most-recent.summary'),
|
|
29
|
+
exactlyOne: ['job-id', 'use-most-recent'],
|
|
30
|
+
}),
|
|
31
|
+
'api-version': Flags.orgApiVersion(),
|
|
32
|
+
};
|
|
33
|
+
async run() {
|
|
34
|
+
const { flags } = await this.parse(DataExportResume);
|
|
35
|
+
const cache = await BulkExportRequestCache.create();
|
|
36
|
+
const resumeOpts = await cache.resolveResumeOptionsFromCache(flags['job-id'] ?? flags['use-most-recent'], flags['api-version']);
|
|
37
|
+
const queryJob = new QueryJobV2(resumeOpts.options.connection, {
|
|
38
|
+
id: resumeOpts.jobInfo.id,
|
|
39
|
+
pollingOptions: {
|
|
40
|
+
// both `pollInterval` and `pollTimeout` values are 0 (set in BulkExportRequestCache.resolveResumeOptionsFromCache).
|
|
41
|
+
// So we set the interval to 5s and timeout to 30s (otherwise jsforce would throw a timeout err if passed 0ms).
|
|
42
|
+
pollInterval: Math.max(resumeOpts.options.pollingOptions.pollInterval, 5000),
|
|
43
|
+
pollTimeout: Math.max(resumeOpts.options.pollingOptions.pollTimeout, 30_000),
|
|
44
|
+
},
|
|
45
|
+
});
|
|
46
|
+
const ms = new MultiStageOutput({
|
|
47
|
+
title: 'Exporting data',
|
|
48
|
+
jsonEnabled: flags.json ?? false,
|
|
49
|
+
stages: ['checking query job status', 'exporting records'],
|
|
50
|
+
postStagesBlock: [
|
|
51
|
+
{
|
|
52
|
+
label: 'Status',
|
|
53
|
+
type: 'dynamic-key-value',
|
|
54
|
+
bold: true,
|
|
55
|
+
get: (data) => data?.state,
|
|
56
|
+
},
|
|
57
|
+
],
|
|
58
|
+
});
|
|
59
|
+
ms.goto('checking query job status');
|
|
60
|
+
queryJob.on('jobComplete', (jobInfo) => {
|
|
61
|
+
ms.goto('exporting records', { state: jobInfo.state });
|
|
62
|
+
});
|
|
63
|
+
queryJob.on('error', (err) => {
|
|
64
|
+
ms.stop('failed');
|
|
65
|
+
throw err;
|
|
66
|
+
});
|
|
67
|
+
try {
|
|
68
|
+
const jobInfo = await exportRecords(resumeOpts.options.connection, queryJob, resumeOpts.outputInfo);
|
|
69
|
+
ms.stop();
|
|
70
|
+
this.log(`${jobInfo.numberRecordsProcessed} records written to ${resumeOpts.outputInfo.filePath}`);
|
|
71
|
+
return {
|
|
72
|
+
totalSize: jobInfo.numberRecordsProcessed,
|
|
73
|
+
filePath: resumeOpts.outputInfo.filePath,
|
|
74
|
+
};
|
|
75
|
+
}
|
|
76
|
+
catch (err) {
|
|
77
|
+
ms.stop('failed');
|
|
78
|
+
throw err;
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
//# sourceMappingURL=resume.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"resume.js","sourceRoot":"","sources":["../../../../src/commands/data/export/resume.ts"],"names":[],"mappings":"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"}
|
package/lib/types.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"types.js","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"types.js","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"AAeA,MAAM,CAAN,IAAY,SAIX;AAJD,WAAY,SAAS;IACnB,2CAAK,CAAA;IACL,2DAAa,CAAA;IACb,2DAAa,CAAA;AACf,CAAC,EAJW,SAAS,KAAT,SAAS,QAIpB;AA+CD,yEAAyE;AACzE,MAAM,CAAC,MAAM,gBAAgB,GAAG,CAAI,OAAgB,EAAoC,EAAE,CACxF,KAAK,CAAC,OAAO,CAAE,OAAiC,EAAE,OAAO,CAAC,CAAC;AAE7D,0EAA0E;AAC1E,MAAM,CAAC,MAAM,wBAAwB,GAAG,CAAI,OAAgB,EAAoC,EAAE,CAChG,gBAAgB,CAAC,OAAO,CAAC,IAAI,OAAO,CAAC,OAAO,CAAC,MAAM,GAAG,CAAC,CAAC;AAE1D,4DAA4D;AAC5D,MAAM,CAAC,MAAM,sBAAsB,GAAG,CAAI,KAAmB,EAA4C,EAAE,CACzG,OAAO,KAAK,CAAC,CAAC,CAAC,KAAK,QAAQ,IAAI,wBAAwB,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC;AAErE,MAAM,CAAC,MAAM,mBAAmB,GAAG,CAAC,OAAgB,EAA6C,EAAE,CACjG,CAAC,CAAE,OAA0C,CAAC,WAAW,IAAI,CAAC,CAAE,OAA0C,CAAC,IAAI,CAAC;AAElH,4DAA4D;AAC5D,MAAM,CAAC,MAAM,iBAAiB,GAAG,CAAC,KAAmB,EAA2D,EAAE,CAChH,KAAK,CAAC,CAAC,CAAC,KAAK,YAAY,IAAI,mBAAmB,CAAC,KAAK,CAAC,CAAC,CAAC,CAAC,CAAC"}
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
# summary
|
|
2
|
+
|
|
3
|
+
Bulk export records from an org into a file using a SOQL query. Uses Bulk API 2.0.
|
|
4
|
+
|
|
5
|
+
# description
|
|
6
|
+
|
|
7
|
+
You can use this command to export millions of records from an org, either to migrate data or to back it up.
|
|
8
|
+
|
|
9
|
+
Use a SOQL query to specify the fields of a standard or custom object that you want to export. Specify the SOQL query either at the command line with the --query flag or read it from a file with the --query-file flag; you can't specify both flags. The --output-file flag is required, which means you can only write the records to a file, in either CSV or JSON format.
|
|
10
|
+
|
|
11
|
+
Bulk exports can take a while, depending on how many records are returned by the SOQL query. If the command times out, or you specified the --async flag, the command displays the job ID. To see the status and get the results of the job, run "sf data export resume" and pass the job ID to the --job-id flag.
|
|
12
|
+
|
|
13
|
+
IMPORTANT: This command uses Bulk API 2.0, which limits the type of SOQL queries you can run. For example, you can't use aggregate functions such as count(). For the complete list of limitations, see the "SOQL Considerations" section in the "Bulk API 2.0 and Bulk API Developer Guide" (https://developer.salesforce.com/docs/atlas.en-us.api_asynch.meta/api_asynch/queries.htm).
|
|
14
|
+
|
|
15
|
+
# examples
|
|
16
|
+
|
|
17
|
+
- Export the Id, Name, and Account.Name fields of the Contact object into a CSV-formatted file; if the export doesn't complete in 10 minutes, the command ends and displays a job ID. Use the org with alias "my-scratch":
|
|
18
|
+
|
|
19
|
+
<%= config.bin %> <%= command.id %> --query "SELECT Id, Name, Account.Name FROM Contact" --output-file export-accounts.csv --wait 10 --target-org my-scratch
|
|
20
|
+
|
|
21
|
+
- Similar to previous example, but use the default org, export the records into a JSON-formatted file, and include records that have been soft deleted:
|
|
22
|
+
|
|
23
|
+
<%= config.bin %> <%= command.id %> --query "SELECT Id, Name, Account.Name FROM Contact" --output-file export-accounts.json --result-format json --wait 10 --all-rows
|
|
24
|
+
|
|
25
|
+
- Export asynchronously; the command immediately returns a job ID that you then pass to the "sf data export resume" command:
|
|
26
|
+
|
|
27
|
+
<%= config.bin %> <%= command.id %> --query "SELECT Id, Name, Account.Name FROM Contact" --output-file export-accounts.json --result-format json --async
|
|
28
|
+
|
|
29
|
+
# flags.wait.summary
|
|
30
|
+
|
|
31
|
+
Time to wait for the command to finish, in minutes.
|
|
32
|
+
|
|
33
|
+
# flags.async.summary
|
|
34
|
+
|
|
35
|
+
Don't wait for the job to complete.
|
|
36
|
+
|
|
37
|
+
# flags.query.summary
|
|
38
|
+
|
|
39
|
+
SOQL query to execute.
|
|
40
|
+
|
|
41
|
+
# flags.all-rows.summary
|
|
42
|
+
|
|
43
|
+
Include records that have been soft-deleted due to a merge or delete. By default, deleted records are not returned.
|
|
44
|
+
|
|
45
|
+
# flags.output-file.summary
|
|
46
|
+
|
|
47
|
+
File where records are written.
|
|
48
|
+
|
|
49
|
+
# flags.result-format.summary
|
|
50
|
+
|
|
51
|
+
Format to write the results.
|
|
52
|
+
|
|
53
|
+
# flags.column-delimiter.summary
|
|
54
|
+
|
|
55
|
+
Column delimiter to be used when writing CSV output. Default is COMMA.
|
|
56
|
+
|
|
57
|
+
# flags.line-ending.summary
|
|
58
|
+
|
|
59
|
+
Line ending to be used when writing CSV output. Default value on Windows is is `CRLF`; on macOS and Linux it's `LR`.
|
|
60
|
+
|
|
61
|
+
# flags.query-file.summary
|
|
62
|
+
|
|
63
|
+
File that contains the SOQL query.
|
|
64
|
+
|
|
65
|
+
# export.timeout
|
|
66
|
+
|
|
67
|
+
Run "sf data export resume --job-id %s" to get the latest status and results.
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
# summary
|
|
2
|
+
|
|
3
|
+
Resume a bulk export job that you previously started.
|
|
4
|
+
|
|
5
|
+
# description
|
|
6
|
+
|
|
7
|
+
When the original "data export bulk" command either times out or is run with the --async flag, it displays a job ID. To see the status and get the results of the bulk export, run this command by either passing it the job ID or using the --use-most-recent flag to specify the most recent bulk export job.
|
|
8
|
+
|
|
9
|
+
# flags.job-id.summary
|
|
10
|
+
|
|
11
|
+
Job ID of the bulk export.
|
|
12
|
+
|
|
13
|
+
# flags.use-most-recent.summary
|
|
14
|
+
|
|
15
|
+
Use the job ID of the bulk export job that was most recently run.
|
|
16
|
+
|
|
17
|
+
# examples
|
|
18
|
+
|
|
19
|
+
- Resume a bulk export job run on your default org by specifying a job ID:
|
|
20
|
+
|
|
21
|
+
sf <%= command.id %> --job-id 750xx000000005sAAA
|
|
22
|
+
|
|
23
|
+
- Resume the most recently-run bulk export job for an org with alias my-scratch:
|
|
24
|
+
|
|
25
|
+
sf data export resume --use-most-recent --target-org my-scratch
|
package/messages/messages.md
CHANGED
|
@@ -52,7 +52,11 @@ Format to display the results; the --json flag overrides this flag.
|
|
|
52
52
|
|
|
53
53
|
The bulk request id must be supplied when not looking for most recent cache entry.
|
|
54
54
|
|
|
55
|
-
#
|
|
55
|
+
# error.bulkRequestIdNotFound
|
|
56
|
+
|
|
57
|
+
Could not find a cache entry for job ID %s
|
|
58
|
+
|
|
59
|
+
# error.missingCacheEntryError
|
|
56
60
|
|
|
57
61
|
Could not load a most recent cache entry for a bulk request. Please rerun your command with a bulk request id.
|
|
58
62
|
|