pageship 0.1.0 → 0.1.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 +3 -2
- package/dist/cli.mjs +5 -32
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -47,8 +47,9 @@ to reuse the stored credential in a new process. Add global `--json` for structu
|
|
|
47
47
|
results. Pending or denied authorization exits 2, success exits 0, request/storage
|
|
48
48
|
failures exit 1, and interrupted waiting exits 130.
|
|
49
49
|
|
|
50
|
-
Credentials
|
|
51
|
-
|
|
50
|
+
Credentials are plaintext JSON outside projects. POSIX uses an owner-only directory
|
|
51
|
+
and 0600 files. Windows uses the current user's local app data and inherits
|
|
52
|
+
user-profile permissions; the CLI does not configure Windows ACLs.
|
|
52
53
|
`PAGESHIP_CONFIG_DIR` selects an absolute private directory. They are bound to the
|
|
53
54
|
exact HTTPS server origin; HTTP is allowed only on loopback for development.
|
|
54
55
|
Use `login --restart` for a new code. Address selection and publication are not
|
package/dist/cli.mjs
CHANGED
|
@@ -829,32 +829,6 @@ async function checkCompatibility(baseUrl, options = {}) {
|
|
|
829
829
|
return evaluateCompatibility(validateCompatibility(data));
|
|
830
830
|
}
|
|
831
831
|
//#endregion
|
|
832
|
-
//#region src/windows-protection.ts
|
|
833
|
-
/** DPAPI binds this ciphertext to the current Windows account on this machine. */
|
|
834
|
-
function windowsProtection(value, operation) {
|
|
835
|
-
const script = `$ErrorActionPreference='Stop'; [Console]::InputEncoding=[Text.Encoding]::UTF8; [Console]::OutputEncoding=[Text.Encoding]::UTF8; Add-Type -AssemblyName System.Security; $value=[Console]::In.ReadToEnd(); [Console]::Out.Write(${operation === "protect" ? "[Convert]::ToBase64String([Security.Cryptography.ProtectedData]::Protect([Text.Encoding]::UTF8.GetBytes($value),$null,[Security.Cryptography.DataProtectionScope]::CurrentUser))" : "[Text.Encoding]::UTF8.GetString([Security.Cryptography.ProtectedData]::Unprotect([Convert]::FromBase64String($value),$null,[Security.Cryptography.DataProtectionScope]::CurrentUser))"})`;
|
|
836
|
-
return new Promise((resolve, reject) => {
|
|
837
|
-
const executable = join(process.env.SystemRoot ?? "C:\\Windows", "System32", "WindowsPowerShell", "v1.0", "powershell.exe");
|
|
838
|
-
const child = execFile(executable, [
|
|
839
|
-
"-NoLogo",
|
|
840
|
-
"-NoProfile",
|
|
841
|
-
"-NonInteractive",
|
|
842
|
-
"-Command",
|
|
843
|
-
script
|
|
844
|
-
], {
|
|
845
|
-
encoding: "utf8",
|
|
846
|
-
windowsHide: true,
|
|
847
|
-
timeout: 1e4,
|
|
848
|
-
maxBuffer: 1048576
|
|
849
|
-
}, (error, stdout) => {
|
|
850
|
-
if (error) reject(/* @__PURE__ */ new Error("Windows protected storage failed. Use this Windows account on this machine and ensure Windows PowerShell and DPAPI are available."));
|
|
851
|
-
else resolve(stdout);
|
|
852
|
-
});
|
|
853
|
-
child.stdin?.on("error", () => {});
|
|
854
|
-
child.stdin?.end(value);
|
|
855
|
-
});
|
|
856
|
-
}
|
|
857
|
-
//#endregion
|
|
858
832
|
//#region src/credential-store.ts
|
|
859
833
|
/** Separate files bind secrets to an exact server origin, outside project directories. */
|
|
860
834
|
async function credentialStore(server, readOnly = false) {
|
|
@@ -887,7 +861,7 @@ async function credentialStore(server, readOnly = false) {
|
|
|
887
861
|
file = await open(path, constants.O_RDONLY | (windows ? 0 : constants.O_NOFOLLOW));
|
|
888
862
|
} catch (error) {
|
|
889
863
|
if (error.code === "ENOENT") return {};
|
|
890
|
-
throw new Error("Could not open
|
|
864
|
+
throw new Error("Could not open credentials. Check the credential file is not a symlink.");
|
|
891
865
|
}
|
|
892
866
|
try {
|
|
893
867
|
const stat = await file.stat();
|
|
@@ -895,9 +869,9 @@ async function credentialStore(server, readOnly = false) {
|
|
|
895
869
|
const raw = await file.readFile("utf8");
|
|
896
870
|
let value;
|
|
897
871
|
try {
|
|
898
|
-
value = JSON.parse(
|
|
872
|
+
value = JSON.parse(raw);
|
|
899
873
|
} catch {
|
|
900
|
-
throw new Error("Could not read
|
|
874
|
+
throw new Error("Could not read credential JSON. Choose a new private PAGESHIP_CONFIG_DIR and log in again.");
|
|
901
875
|
}
|
|
902
876
|
if (!value || typeof value !== "object") throw new Error("Invalid credential file. Start again with a new private PAGESHIP_CONFIG_DIR.");
|
|
903
877
|
const candidate = value;
|
|
@@ -915,8 +889,7 @@ async function credentialStore(server, readOnly = false) {
|
|
|
915
889
|
try {
|
|
916
890
|
const file = await open(temporary, "wx", 384);
|
|
917
891
|
try {
|
|
918
|
-
|
|
919
|
-
await file.writeFile(windows ? await windowsProtection(serialized, "protect") : serialized);
|
|
892
|
+
await file.writeFile(JSON.stringify(value));
|
|
920
893
|
await file.sync();
|
|
921
894
|
} finally {
|
|
922
895
|
await file.close();
|
|
@@ -1426,7 +1399,7 @@ async function publish(options) {
|
|
|
1426
1399
|
}
|
|
1427
1400
|
//#endregion
|
|
1428
1401
|
//#region package.json
|
|
1429
|
-
var version = "0.1.
|
|
1402
|
+
var version = "0.1.1";
|
|
1430
1403
|
//#endregion
|
|
1431
1404
|
//#region src/cli.ts
|
|
1432
1405
|
const args = process.argv.slice(2);
|