cfdns 2.1.2 → 2.2.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/README.md CHANGED
@@ -1,5 +1,5 @@
1
1
  # cfdns
2
- [![](https://img.shields.io/npm/v/cfdns.svg?style=flat)](https://www.npmjs.org/package/cfdns) [![](https://img.shields.io/npm/dm/cfdns.svg)](https://www.npmjs.org/package/cfdns) [![](https://api.travis-ci.org/silverwind/cfdns.svg?style=flat)](https://travis-ci.org/silverwind/cfdns)
2
+ [![](https://img.shields.io/npm/v/cfdns.svg?style=flat)](https://www.npmjs.org/package/cfdns) [![](https://img.shields.io/npm/dm/cfdns.svg)](https://www.npmjs.org/package/cfdns) [![](https://packagephobia.com/badge?p=cfdns)](https://packagephobia.com/result?p=cfdns) [![](https://api.travis-ci.org/silverwind/cfdns.svg?style=flat)](https://travis-ci.org/silverwind/cfdns)
3
3
 
4
4
  > CLI to modify DNS records hosted on Cloudflare
5
5
 
@@ -22,6 +22,8 @@ usage: cfdns [options] command [args]
22
22
  logout Log out from the API
23
23
 
24
24
  Options:
25
+ -c, --color Force-enable color output
26
+ -n, --no-color Disable color output
25
27
  -v, --version Print the version
26
28
  -h, --help Print this help
27
29
 
@@ -0,0 +1 @@
1
+ export {}
package/dist/index.js ADDED
@@ -0,0 +1,21 @@
1
+ #!/usr/bin/env node
2
+ import{parseArgs as e,styleText as t}from"node:util";import{join as n}from"node:path";import{homedir as r}from"node:os";import{chmod as i,readFile as a,unlink as o,writeFile as s}from"node:fs/promises";import{argv as c,exit as l}from"node:process";var u=`2.2.0`;function d(t){try{return e(t)}catch(e){return h(e.message)}}const{values:f,positionals:p}=d({args:c.slice(2),options:{color:{type:`boolean`,short:`c`},help:{type:`boolean`,short:`h`},"no-color":{type:`boolean`,short:`n`},version:{type:`boolean`,short:`v`}},allowPositionals:!0,strict:!0});function m(e,n){return f[`no-color`]?n:t(e,n,{validateStream:!f.color})}function h(e){e&&console.info(`Error: ${e}`),l(+!!e)}f.version&&(console.info(u),h());const g={login:[2,2],logout:[0,0],get:[2,2],set:[3,4],add:[3,4],del:[2,2]},[_,...v]=p,y=_&&g[_]&&v.length>=g[_][0]&&v.length<=g[_][1];(!_||f.help||!Object.keys(g).includes(_)||!y)&&(console.info(`usage: cfdns [options] command [args]
3
+
4
+ Commands:
5
+ login <email> <key> Log in to the API
6
+ get <name> <type> Retrieve a DNS record
7
+ set <name> <type> <value> [<ttl>] Create or update a DNS record
8
+ del <name> <type> Delete a DNS record
9
+ logout Log out from the API
10
+
11
+ Options:
12
+ -c, --color Force-enable color output
13
+ -n, --no-color Disable color output
14
+ -v, --version Print the version
15
+ -h, --help Print this help
16
+
17
+ Example:
18
+ $ cfdns login user@example.com 4c689aa3462a44a121c1f199c1081240b9be4
19
+ $ cfdns set example.com a 1.2.3.4 120
20
+ $ cfdns get example.com a
21
+ $ cfdns del example.com a`),h());let b,x;async function S(e,t,n){let r=await fetch(`https://api.cloudflare.com/client/v4/${t}`,{method:e.toUpperCase(),headers:{"Content-Type":`application/json`,"X-Auth-Email":b,"X-Auth-Key":x},body:n===void 0?void 0:JSON.stringify(n)}),i=await r.json();if(!r.ok)throw Error(`${r.status} ${r.statusText}: ${JSON.stringify(i)}`);return i.result}const C=n(r(),`.cfdnsrc`);if(_===`login`||_===`logout`){if(_===`login`)[b,x]=v,await s(C,JSON.stringify({email:b,key:x})),await i(C,384),console.info(`login data saved`);else try{await o(C),console.info(`login data deleted`)}catch{console.info(`no login data found`)}h()}else try{({email:b,key:x}=JSON.parse(await a(C,`utf8`)))}catch{h(`login data not found, please log in first.`)}v[1]&&=v[1].toUpperCase();let[w,T,E,D]=v;D||=120,typeof D==`string`&&(D=Number(D));const O=(await S(`get`,`zones`)).find(e=>w.endsWith(e.name));O||h(`no matching zone found`);const k=(await S(`get`,`zones/${O.id}/dns_records?name=${w}&type=${T}`))[0];_===`get`?console.info(k):_===`set`||_===`add`?k?E!==k.content||D!==k.ttl?(await S(`put`,`zones/${O.id}/dns_records/${k.id}`,{name:w,type:T,content:E,ttl:D,proxied:k.proxied}),console.info(`updated ${m(`magenta`,w)} ${D} IN ${T} ${m(`green`,E)}`)):console.info(`${m(`magenta`,w)} is up to date`):(await S(`post`,`zones/${O.id}/dns_records`,{name:w,type:T,content:E,ttl:D,proxied:!1}),console.info(`created ${m(`magenta`,w)} ${D} IN ${T} ${m(`green`,E)}`)):_===`del`&&k&&(await S(`delete`,`zones/${O.id}/dns_records/${k.id}`),console.info(`deleted ${m(`magenta`,w)} ${k.ttl} IN ${T} ${m(`green`,k.content)}`)),h();export{};
package/package.json CHANGED
@@ -1,19 +1,24 @@
1
1
  {
2
2
  "name": "cfdns",
3
- "version": "2.1.2",
3
+ "version": "2.2.0",
4
4
  "description": "CLI to modify DNS records hosted on Cloudflare",
5
5
  "author": "silverwind <me@silverwind.io>",
6
- "repository": "silverwind/cfdns",
6
+ "repository": {
7
+ "type": "git",
8
+ "url": "git+https://github.com/silverwind/cfdns.git"
9
+ },
7
10
  "type": "module",
11
+ "sideEffects": false,
8
12
  "license": "BSD-2-Clause",
9
- "engines": {
10
- "node": ">=8"
11
- },
12
13
  "bin": {
13
- "cfdns": "cfdns.js"
14
+ "cfdns": "./dist/index.js"
15
+ },
16
+ "engines": {
17
+ "node": ">=22",
18
+ "bun": "*"
14
19
  },
15
20
  "files": [
16
- "cfdns.js"
21
+ "dist"
17
22
  ],
18
23
  "keywords": [
19
24
  "cloudflare",
@@ -23,22 +28,17 @@
23
28
  "record",
24
29
  "ddns"
25
30
  ],
26
- "dependencies": {
27
- "chalk": "5.6.2",
28
- "fs-extra": "^11.3.3",
29
- "minimist": "^1.2.8",
30
- "request": "^2.88.2",
31
- "request-promise-native": "^1.0.9",
32
- "ver": "6.0.2"
33
- },
34
31
  "devDependencies": {
35
- "eslint": "^9.39.2",
36
- "eslint-config-silverwind": "^121.0.5",
37
- "typescript-config-silverwind": "15.0.0",
38
- "updates": "^17.5.2",
39
- "updates-config-silverwind": "1.0.3"
40
- },
41
- "scripts": {
42
- "test": "make test"
32
+ "@types/node": "26.6.2",
33
+ "@typescript/native-preview": "7.0.0-dev.20260707.2",
34
+ "eslint": "10.11.0",
35
+ "eslint-config-silverwind": "151.0.0",
36
+ "tsdown": "0.23.0",
37
+ "tsdown-config-silverwind": "4.1.1",
38
+ "typescript": "6.0.3",
39
+ "typescript-config-silverwind": "21.0.0",
40
+ "updates": "19.0.0",
41
+ "updates-config-silverwind": "4.0.6",
42
+ "versions": "15.5.0"
43
43
  }
44
44
  }
package/cfdns.js DELETED
@@ -1,148 +0,0 @@
1
- #!/usr/bin/env node
2
- import minimist from "minimist";
3
- import request from "request-promise-native";
4
- import chalk from "chalk";
5
- import fs from "fs-extra";
6
- import {join} from "node:path";
7
- import {homedir} from "node:os";
8
- import {readFileSync} from "node:fs";
9
-
10
- const pkg = JSON.parse(readFileSync(new URL("package.json", import.meta.url)));
11
-
12
- const args = minimist(process.argv.slice(2), {
13
- boolean: [
14
- "c", "color",
15
- "h", "help",
16
- "n", "no-color",
17
- "v", "version",
18
- ],
19
- string: [
20
- "_",
21
- ],
22
- alias: {
23
- c: "color",
24
- h: "help",
25
- n: "no-color",
26
- v: "version",
27
- },
28
- });
29
-
30
- function exit(err) {
31
- if (err) console.info(`Error: ${err}`);
32
- process.exit(err ? 1 : 0);
33
- }
34
-
35
- if (args.version) {
36
- console.info(pkg.version);
37
- exit();
38
- }
39
-
40
- const cmds = {
41
- login: [2, 2],
42
- logout: [0, 0],
43
- get: [2, 2],
44
- set: [3, 4],
45
- add: [3, 4],
46
- del: [2, 2],
47
- };
48
-
49
- const [cmd, ...params] = args._;
50
- const paramLengthOkay = cmd && cmds[cmd] && (params.length >= cmds[cmd][0] && params.length <= cmds[cmd][1]);
51
- if (!cmd || args.help || !Object.keys(cmds).includes(cmd) || !paramLengthOkay) {
52
- console.info(`usage: cfdns [options] command [args]
53
-
54
- Commands:
55
- login <email> <key> Log in to the API
56
- get <name> <type> Retrieve a DNS record
57
- set <name> <type> <value> [<ttl>] Create or update a DNS record
58
- del <name> <type> Delete a DNS record
59
- logout Log out from the API
60
-
61
- Options:
62
- -c, --color Force-enable color output
63
- -n, --no-color Disable color output
64
- -v, --version Print the version
65
- -h, --help Print this help
66
-
67
- Example:
68
- $ cfdns login user@example.com 4c689aa3462a44a121c1f199c1081240b9be4
69
- $ cfdns set example.com a 1.2.3.4 120
70
- $ cfdns get example.com a
71
- $ cfdns del example.com a`);
72
- exit();
73
- }
74
-
75
- let email, key;
76
-
77
- async function req(method, path, body) {
78
- return (await request({
79
- method: method.toUpperCase(),
80
- json: true,
81
- uri: `https://api.cloudflare.com/client/v4/${path}`,
82
- headers: {
83
- "X-Auth-Email": email,
84
- "X-Auth-Key": key,
85
- },
86
- body,
87
- })).result;
88
- }
89
-
90
- (async () => {
91
- const rcfile = join(homedir(), ".cfdnsrc");
92
-
93
- if (cmd === "login" || cmd === "logout") {
94
- if (cmd === "login") {
95
- [email, key] = params;
96
- await fs.writeFile(rcfile, JSON.stringify({email, key}));
97
- await fs.chmod(rcfile, 0o600);
98
- console.info("login data saved");
99
- } else {
100
- try {
101
- await fs.unlink(rcfile);
102
- console.info("login data deleted");
103
- } catch {
104
- console.info("no login data found");
105
- }
106
- }
107
- exit();
108
- } else {
109
- try {
110
- ({email, key} = JSON.parse(await fs.readFile(rcfile)));
111
- } catch {
112
- exit("login data not found, please log in first.");
113
- }
114
- }
115
-
116
- if (params[1]) params[1] = params[1].toUpperCase();
117
- let [name, type, content, ttl] = params;
118
- if (!ttl) ttl = 120;
119
- if (typeof ttl === "string") ttl = Number(ttl);
120
- const zones = await req("get", "zones");
121
- const zone = zones.find(zone => name.endsWith(zone.name));
122
- if (!zone) exit("no matching zone found");
123
-
124
- const record = (await req("get", `zones/${zone.id}/dns_records?name=${name}&type=${type}`))[0];
125
- if (cmd === "get") {
126
- console.info(record);
127
- } else if (cmd === "set" || cmd === "add") {
128
- if (record) {
129
- if (content !== record.content || ttl !== record.ttl) {
130
- await req("put", `zones/${zone.id}/dns_records/${record.id}`, {
131
- name, type, content, ttl, proxied: record.proxied
132
- });
133
- console.info(`updated ${chalk.magenta(name)} ${ttl} IN ${type} ${chalk.green(content)}`);
134
- } else {
135
- console.info(`${chalk.magenta(name)} is up to date`);
136
- }
137
- } else {
138
- await req("post", `zones/${zone.id}/dns_records`, {
139
- name, type, content, ttl, proxied: false
140
- });
141
- console.info(`created ${chalk.magenta(name)} ${ttl} IN ${type} ${chalk.green(content)}`);
142
- }
143
- } else if (cmd === "del" && record) {
144
- await req("delete", `zones/${zone.id}/dns_records/${record.id}`);
145
- console.info(`deleted ${chalk.magenta(name)} ${record.ttl} IN ${type} ${chalk.green(record.content)}`);
146
- }
147
- exit();
148
- })();