code-push-itspar 1.0.0

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/LICENSE.txt ADDED
@@ -0,0 +1,22 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2025 Dream Sports Labs
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
22
+
package/README.md ADDED
@@ -0,0 +1,174 @@
1
+ # CodePush CLI
2
+
3
+ The **CodePush CLI** is a Node.js application that allows users to deploy and manage over-the-air updates for React Native applications.
4
+
5
+ ## Installation & Usage
6
+
7
+ ### Global Installation
8
+ ```bash
9
+ npm install -g code-push-itspar
10
+ ```
11
+
12
+ Or using yarn:
13
+ ```bash
14
+ yarn global add code-push-itspar
15
+ ```
16
+
17
+ After global installation, you can use the CLI directly:
18
+ ```bash
19
+ code-push-itspar <command>
20
+ ```
21
+
22
+ ### Project Installation
23
+ ```bash
24
+ # Using npm
25
+ npm install --save-dev code-push-itspar
26
+
27
+ # Using yarn
28
+ yarn add --dev code-push-itspar
29
+ ```
30
+ After project installation, you can use the CLI through npm/yarn:
31
+ ```bash
32
+ # Using npm
33
+ npm run code-push-itspar <command>
34
+
35
+ # Using yarn
36
+ yarn code-push-itspar <command>
37
+
38
+ # Using npx
39
+ npx code-push-itspar <command>
40
+ ```
41
+
42
+ ## Authentication
43
+
44
+ Most commands require authentication. You'll need an access key and server URL to use the CLI.
45
+
46
+ ### Login
47
+ ```bash
48
+ # Login with access key and server URL
49
+ code-push-itspar login --accessKey <your-access-key> <server-url>
50
+
51
+ # Example
52
+ code-push-itspar login --accessKey abc123xyz https://codepush.jaswantdhayal.com
53
+
54
+ # Check login status
55
+ code-push-itspar whoami
56
+
57
+ # Logout
58
+ code-push-itspar logout
59
+ ```
60
+
61
+ To get an access key:
62
+
63
+ 1. Visit your CodePush Dashboard
64
+ 2. Go to Settings → Generate New Token
65
+ 3. Generate a new access key
66
+
67
+ ## Release Management
68
+
69
+ The `release` command allows you to deploy updates to your app. There are two types of updates you can release:
70
+
71
+ 1. Full Bundle (sending fully updated bundle)
72
+ 2. Patch Bundle (sending only the diff)
73
+
74
+ ### Command Structure
75
+ ```bash
76
+ code-push-itspar release <appName> <updateContents> <targetBinaryVersion>
77
+ [--deploymentName <deploymentName>]
78
+ [--description <description>]
79
+ [--disabled <disabled>]
80
+ [--mandatory]
81
+ [--noDuplicateReleaseError]
82
+ [--rollout <rolloutPercentage>]
83
+ [--isPatch <true|false>] # Default false. Specify true in case sending patch bundle.
84
+ [--compression <'deflate' | 'brotli'>] # 'deflate' (default) or 'brotli' (better compression)
85
+ ```
86
+
87
+ Parameters:
88
+
89
+ Required Parameters:
90
+ - `appName`: Name of your app (e.g., "MyApp-iOS")
91
+ - `updateContents`: Path to your update files (bundle/assets)
92
+ - `targetBinaryVersion`: App store version this update is for. Can be:
93
+ - Exact version: "1.0.0"
94
+ - Range: "^1.0.0" (compatible with 1.x.x)
95
+ - Wildcard: "*" (all versions)
96
+
97
+ Optional Parameters:
98
+ - `--deploymentName` or `-d`: Target deployment ("Staging" or "Production", defaults to "Staging")
99
+ - `--description` or `-des`: Release notes or changelog
100
+ - `--disabled`: Prevents update from being downloaded (useful for staged rollouts)
101
+ - `--mandatory`: Forces users to accept this update
102
+ - `--noDuplicateReleaseError`: Shows warning instead of error if releasing same content
103
+ - `--rollout`: Percentage of users who should receive this update (1-100)
104
+ - `--isPatch`: Whether this is a patch update
105
+ - `false` (default): Full bundle update
106
+ - `true`: Patch update (requires patch bundle)
107
+ - `--compression`: Compression algorithm to use
108
+ - `deflate` (default): Standard compression
109
+ - `brotli`: Better compression, smaller bundle size
110
+
111
+ ### Full Bundle Release
112
+ Release a complete new bundle:
113
+ ```bash
114
+ # Release to staging with deflate compression (default)
115
+ code-push-itspar release MyApp-iOS ./codepush 1.0.0 \
116
+ --deploymentName Staging \
117
+ --description "New features" \
118
+ --isPatch false
119
+
120
+ # Release with brotli compression (better compression)
121
+ code-push-itspar release MyApp-iOS ./dist/bundle "^1.0.0" \
122
+ --deploymentName Production \
123
+ --mandatory \
124
+ --isPatch false \
125
+ --compression brotli
126
+ ```
127
+
128
+ > Note about compression: Brotli typically achieves better compression ratios than deflate (e.g., 23.1MB → 8.14MB with Brotli vs 11.04MB with deflate).
129
+
130
+ ### Patch Bundle Release
131
+ For smaller updates, first create a patch and then release it:
132
+
133
+ 1. Create patch between old and new bundles:
134
+ ```bash
135
+ code-push-itspar create-patch \
136
+ ./old-bundle \
137
+ ./new-bundle \
138
+ ./.codepush/patches
139
+ ```
140
+
141
+ 2. Release the patch:
142
+ ```bash
143
+ # Release patch with brotli compression
144
+ code-push-itspar release MyApp-iOS ./.codeupush/patches "1.0.0" \
145
+ --deploymentName Staging \
146
+ --description "Bug fixes" \
147
+ --isPatch true \
148
+ --compression brotli
149
+ ```
150
+
151
+ > Note about patches: Patch updates significantly reduce the update size as they only contain the changes between versions. Always use `--isPatch true` when releasing a patch bundle.
152
+
153
+ _Note: Make sure to upload assets alongwith patch bundle._
154
+
155
+ For more details about the binary diff implementation, see [bsdiff/README.md](./bsdiff/README.md).
156
+
157
+ ### Promote Updates
158
+ After testing in staging, promote to production:
159
+ ```bash
160
+ # Basic promotion
161
+ code-push-itspar promote MyApp-iOS Staging Production
162
+
163
+ # Promotion with options
164
+ code-push-itspar promote MyApp-iOS Staging Production \
165
+ --rollout 25 \ # Release to 25% of users
166
+ --description "Verified update" # Update description
167
+ ```
168
+
169
+ ## Contributing
170
+
171
+ For information about contributing to CodePush CLI, please see our [Contributing Guide](./CONTRIBUTING.md).
172
+
173
+ ---
174
+ **Note:** For additional commands and advanced features, see our [Advanced Usage Guide](./CLI_REFERENCE.md).
@@ -0,0 +1,178 @@
1
+ "use strict";
2
+ // Copyright (c) Microsoft Corporation.
3
+ // Licensed under the MIT License.
4
+ Object.defineProperty(exports, "__esModule", { value: true });
5
+ exports.AcquisitionManager = exports.AcquisitionStatus = void 0;
6
+ class AcquisitionStatus {
7
+ static DeploymentSucceeded = "DeploymentSucceeded";
8
+ static DeploymentFailed = "DeploymentFailed";
9
+ }
10
+ exports.AcquisitionStatus = AcquisitionStatus;
11
+ class AcquisitionManager {
12
+ _appVersion;
13
+ _clientUniqueId;
14
+ _deploymentKey;
15
+ _httpRequester;
16
+ _ignoreAppVersion;
17
+ _serverUrl;
18
+ constructor(httpRequester, configuration) {
19
+ this._httpRequester = httpRequester;
20
+ this._serverUrl = configuration.serverUrl;
21
+ if (this._serverUrl.slice(-1) !== "/") {
22
+ this._serverUrl += "/";
23
+ }
24
+ this._appVersion = configuration.appVersion;
25
+ this._clientUniqueId = configuration.clientUniqueId;
26
+ this._deploymentKey = configuration.deploymentKey;
27
+ this._ignoreAppVersion = configuration.ignoreAppVersion;
28
+ }
29
+ queryUpdateWithCurrentPackage(currentPackage, callback) {
30
+ if (!currentPackage || !currentPackage.appVersion) {
31
+ throw new Error("Calling common acquisition SDK with incorrect package"); // Unexpected; indicates error in our implementation
32
+ }
33
+ const updateRequest = {
34
+ deploymentKey: this._deploymentKey,
35
+ appVersion: currentPackage.appVersion,
36
+ packageHash: currentPackage.packageHash,
37
+ isCompanion: this._ignoreAppVersion,
38
+ label: currentPackage.label,
39
+ clientUniqueId: this._clientUniqueId,
40
+ };
41
+ const requestUrl = this._serverUrl + "updateCheck?" + queryStringify(updateRequest);
42
+ this._httpRequester.request(0 /* Http.Verb.GET */, requestUrl, (error, response) => {
43
+ if (error) {
44
+ callback(error, /*remotePackage=*/ null);
45
+ return;
46
+ }
47
+ if (response.statusCode !== 200) {
48
+ callback(new Error(response.statusCode + ": " + response.body), /*remotePackage=*/ null);
49
+ return;
50
+ }
51
+ let updateInfo;
52
+ try {
53
+ const responseObject = JSON.parse(response.body);
54
+ updateInfo = responseObject.updateInfo;
55
+ }
56
+ catch (error) {
57
+ callback(error, /*remotePackage=*/ null);
58
+ return;
59
+ }
60
+ if (!updateInfo) {
61
+ callback(error, /*remotePackage=*/ null);
62
+ return;
63
+ }
64
+ else if (updateInfo.updateAppVersion) {
65
+ callback(/*error=*/ null, {
66
+ updateAppVersion: true,
67
+ appVersion: updateInfo.appVersion,
68
+ });
69
+ return;
70
+ }
71
+ else if (!updateInfo.isAvailable) {
72
+ callback(/*error=*/ null, /*remotePackage=*/ null);
73
+ return;
74
+ }
75
+ const remotePackage = {
76
+ deploymentKey: this._deploymentKey,
77
+ description: updateInfo.description,
78
+ label: updateInfo.label,
79
+ appVersion: updateInfo.appVersion,
80
+ isMandatory: updateInfo.isMandatory,
81
+ packageHash: updateInfo.packageHash,
82
+ packageSize: updateInfo.packageSize,
83
+ downloadUrl: updateInfo.downloadURL,
84
+ };
85
+ callback(/*error=*/ null, remotePackage);
86
+ });
87
+ }
88
+ reportStatusDeploy(deployedPackage, status, previousLabelOrAppVersion, previousDeploymentKey, callback) {
89
+ const url = this._serverUrl + "reportStatus/deploy";
90
+ const body = {
91
+ appVersion: this._appVersion,
92
+ deploymentKey: this._deploymentKey,
93
+ };
94
+ if (this._clientUniqueId) {
95
+ body.clientUniqueId = this._clientUniqueId;
96
+ }
97
+ if (deployedPackage) {
98
+ body.label = deployedPackage.label;
99
+ body.appVersion = deployedPackage.appVersion;
100
+ switch (status) {
101
+ case AcquisitionStatus.DeploymentSucceeded:
102
+ case AcquisitionStatus.DeploymentFailed:
103
+ body.status = status;
104
+ break;
105
+ default:
106
+ if (callback) {
107
+ if (!status) {
108
+ callback(new Error("Missing status argument."), /*not used*/ null);
109
+ }
110
+ else {
111
+ callback(new Error('Unrecognized status "' + status + '".'), /*not used*/ null);
112
+ }
113
+ }
114
+ return;
115
+ }
116
+ }
117
+ if (previousLabelOrAppVersion) {
118
+ body.previousLabelOrAppVersion = previousLabelOrAppVersion;
119
+ }
120
+ if (previousDeploymentKey) {
121
+ body.previousDeploymentKey = previousDeploymentKey;
122
+ }
123
+ callback = typeof arguments[arguments.length - 1] === "function" && arguments[arguments.length - 1];
124
+ this._httpRequester.request(2 /* Http.Verb.POST */, url, JSON.stringify(body), (error, response) => {
125
+ if (callback) {
126
+ if (error) {
127
+ callback(error, /*not used*/ null);
128
+ return;
129
+ }
130
+ if (response.statusCode !== 200) {
131
+ callback(new Error(response.statusCode + ": " + response.body), /*not used*/ null);
132
+ return;
133
+ }
134
+ callback(/*error*/ null, /*not used*/ null);
135
+ }
136
+ });
137
+ }
138
+ reportStatusDownload(downloadedPackage, callback) {
139
+ const url = this._serverUrl + "reportStatus/download";
140
+ const body = {
141
+ clientUniqueId: this._clientUniqueId,
142
+ deploymentKey: this._deploymentKey,
143
+ label: downloadedPackage.label,
144
+ };
145
+ this._httpRequester.request(2 /* Http.Verb.POST */, url, JSON.stringify(body), (error, response) => {
146
+ if (callback) {
147
+ if (error) {
148
+ callback(error, /*not used*/ null);
149
+ return;
150
+ }
151
+ if (response.statusCode !== 200) {
152
+ callback(new Error(response.statusCode + ": " + response.body), /*not used*/ null);
153
+ return;
154
+ }
155
+ callback(/*error*/ null, /*not used*/ null);
156
+ }
157
+ });
158
+ }
159
+ }
160
+ exports.AcquisitionManager = AcquisitionManager;
161
+ function queryStringify(object) {
162
+ let queryString = "";
163
+ let isFirst = true;
164
+ for (const property in object) {
165
+ if (object.hasOwnProperty(property)) {
166
+ const value = object[property];
167
+ if (!isFirst) {
168
+ queryString += "&";
169
+ }
170
+ queryString += encodeURIComponent(property) + "=";
171
+ if (value !== null && typeof value !== "undefined") {
172
+ queryString += encodeURIComponent(value);
173
+ }
174
+ isFirst = false;
175
+ }
176
+ }
177
+ return queryString;
178
+ }
@@ -0,0 +1,23 @@
1
+ #!/usr/bin/env node
2
+ "use strict";
3
+ // Copyright (c) Microsoft Corporation.
4
+ // Licensed under the MIT License.
5
+ Object.defineProperty(exports, "__esModule", { value: true });
6
+ const parser = require("./command-parser");
7
+ const execute = require("./command-executor");
8
+ const chalk = require("chalk");
9
+ function run() {
10
+ const command = parser.createCommand();
11
+ if (!command) {
12
+ parser.showHelp(/*showRootDescription*/ false);
13
+ return;
14
+ }
15
+ execute
16
+ .execute(command)
17
+ .catch((error) => {
18
+ console.error(chalk.red(`[Error] ${error.message}`));
19
+ process.exit(1);
20
+ })
21
+ .done();
22
+ }
23
+ run();