kintone-migrator 0.1.2 → 0.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.
Files changed (3) hide show
  1. package/README.md +14 -0
  2. package/dist/index.mjs +87 -66
  3. package/package.json +6 -1
package/README.md CHANGED
@@ -19,19 +19,33 @@ Connection details for kintone can be specified via CLI arguments or environment
19
19
  | CLI Argument | Environment Variable | Description |
20
20
  |---------|----------|------|
21
21
  | `--domain`, `-d` | `KINTONE_DOMAIN` | kintone domain (e.g., `example.cybozu.com`) |
22
+ | `--api-token`, `-t` | `KINTONE_API_TOKEN` | kintone API token |
22
23
  | `--username`, `-u` | `KINTONE_USERNAME` | kintone username |
23
24
  | `--password`, `-p` | `KINTONE_PASSWORD` | kintone password |
24
25
  | `--app-id`, `-a` | `KINTONE_APP_ID` | kintone app ID |
25
26
  | `--schema-file`, `-f` | `SCHEMA_FILE_PATH` | Schema file path (default: `schema.yaml`) |
26
27
 
28
+ ### Authentication
29
+
30
+ Two authentication methods are supported:
31
+
32
+ - **API Token** (`KINTONE_API_TOKEN`): Recommended. Scoped per app for better security. Multiple tokens can be specified as a comma-separated string (e.g., `token1,token2`).
33
+ - **Username/Password** (`KINTONE_USERNAME` / `KINTONE_PASSWORD`): Basic authentication with user credentials.
34
+
35
+ If both are provided, API Token takes priority. At least one method must be configured.
36
+
27
37
  ### .env File
28
38
 
29
39
  Environment variables can also be defined in a `.env` file and loaded with `dotenv-cli` or similar tools.
30
40
 
31
41
  ```env
32
42
  KINTONE_DOMAIN=example.cybozu.com
43
+
44
+ # Authentication: Use either API Token or Username/Password (API Token takes priority)
45
+ # KINTONE_API_TOKEN=your_api_token
33
46
  KINTONE_USERNAME=your_username
34
47
  KINTONE_PASSWORD=your_password
48
+
35
49
  KINTONE_APP_ID=123
36
50
  SCHEMA_FILE_PATH=schema.yaml
37
51
  ```
package/dist/index.mjs CHANGED
@@ -4,11 +4,95 @@ import { cli, define } from "gunshi";
4
4
  import * as p from "@clack/prompts";
5
5
  import pc from "picocolors";
6
6
  import { KintoneRestAPIClient, KintoneRestAPIError } from "@kintone/rest-api-client";
7
+ import * as v from "valibot";
7
8
  import { mkdir, readFile, writeFile } from "node:fs/promises";
8
9
  import { dirname } from "node:path";
9
10
  import { parse, stringify } from "yaml";
10
- import * as v from "valibot";
11
11
 
12
+ //#region src/cli/config.ts
13
+ const CliConfigSchema = v.object({
14
+ KINTONE_DOMAIN: v.pipe(v.string(), v.nonEmpty("KINTONE_DOMAIN is required")),
15
+ KINTONE_API_TOKEN: v.optional(v.string()),
16
+ KINTONE_USERNAME: v.optional(v.string()),
17
+ KINTONE_PASSWORD: v.optional(v.string()),
18
+ KINTONE_APP_ID: v.pipe(v.string(), v.nonEmpty("KINTONE_APP_ID is required")),
19
+ SCHEMA_FILE_PATH: v.optional(v.string(), "schema.yaml")
20
+ });
21
+ function buildKintoneAuth(auth) {
22
+ if (auth.type === "apiToken") return { apiToken: auth.apiToken };
23
+ return {
24
+ username: auth.username,
25
+ password: auth.password
26
+ };
27
+ }
28
+ const kintoneArgs = {
29
+ domain: {
30
+ type: "string",
31
+ short: "d",
32
+ description: "kintone domain (overrides KINTONE_DOMAIN env var)"
33
+ },
34
+ username: {
35
+ type: "string",
36
+ short: "u",
37
+ description: "kintone username (overrides KINTONE_USERNAME env var)"
38
+ },
39
+ password: {
40
+ type: "string",
41
+ short: "p",
42
+ description: "kintone password (overrides KINTONE_PASSWORD env var)"
43
+ },
44
+ "api-token": {
45
+ type: "string",
46
+ short: "t",
47
+ description: "kintone API token (overrides KINTONE_API_TOKEN env var)"
48
+ },
49
+ "app-id": {
50
+ type: "string",
51
+ short: "a",
52
+ description: "kintone app ID (overrides KINTONE_APP_ID env var)"
53
+ },
54
+ "schema-file": {
55
+ type: "string",
56
+ short: "f",
57
+ description: "Schema file path (default: schema.yaml)"
58
+ }
59
+ };
60
+ function resolveConfig(cliValues) {
61
+ const result = v.safeParse(CliConfigSchema, {
62
+ KINTONE_DOMAIN: cliValues.domain ?? process.env.KINTONE_DOMAIN ?? "",
63
+ KINTONE_API_TOKEN: cliValues["api-token"] ?? process.env.KINTONE_API_TOKEN ?? void 0,
64
+ KINTONE_USERNAME: cliValues.username ?? process.env.KINTONE_USERNAME ?? void 0,
65
+ KINTONE_PASSWORD: cliValues.password ?? process.env.KINTONE_PASSWORD ?? void 0,
66
+ KINTONE_APP_ID: cliValues["app-id"] ?? process.env.KINTONE_APP_ID ?? "",
67
+ SCHEMA_FILE_PATH: cliValues["schema-file"] ?? process.env.SCHEMA_FILE_PATH
68
+ });
69
+ if (!result.success) {
70
+ const missing = result.issues.map((issue) => issue.message).join("\n ");
71
+ throw new Error(`Missing required configuration:\n ${missing}`);
72
+ }
73
+ const { output } = result;
74
+ const auth = resolveAuth(output.KINTONE_API_TOKEN, output.KINTONE_USERNAME, output.KINTONE_PASSWORD);
75
+ return {
76
+ baseUrl: `https://${output.KINTONE_DOMAIN}`,
77
+ auth,
78
+ appId: output.KINTONE_APP_ID,
79
+ schemaFilePath: output.SCHEMA_FILE_PATH
80
+ };
81
+ }
82
+ function resolveAuth(apiToken, username, password) {
83
+ if (apiToken) return {
84
+ type: "apiToken",
85
+ apiToken: apiToken.includes(",") ? apiToken.split(",").map((t) => t.trim()) : apiToken
86
+ };
87
+ if (username && password) return {
88
+ type: "password",
89
+ username,
90
+ password
91
+ };
92
+ throw new Error("Missing required configuration:\n Either KINTONE_API_TOKEN or KINTONE_USERNAME/KINTONE_PASSWORD is required");
93
+ }
94
+
95
+ //#endregion
12
96
  //#region src/lib/error.ts
13
97
  var AnyError = class extends Error {
14
98
  constructor(message, cause) {
@@ -548,10 +632,7 @@ function isNodeError(error) {
548
632
  function createCliContainer(config) {
549
633
  const client = new KintoneRestAPIClient({
550
634
  baseUrl: config.baseUrl,
551
- auth: {
552
- username: config.username,
553
- password: config.password
554
- }
635
+ auth: buildKintoneAuth(config.auth)
555
636
  });
556
637
  return {
557
638
  formConfigurator: new KintoneFormConfigurator(client, config.appId),
@@ -749,63 +830,6 @@ async function saveSchema({ container, input }) {
749
830
  await container.schemaStorage.update(input.schemaText);
750
831
  }
751
832
 
752
- //#endregion
753
- //#region src/cli/config.ts
754
- const CliConfigSchema = v.object({
755
- KINTONE_DOMAIN: v.pipe(v.string(), v.nonEmpty("KINTONE_DOMAIN is required")),
756
- KINTONE_USERNAME: v.pipe(v.string(), v.nonEmpty("KINTONE_USERNAME is required")),
757
- KINTONE_PASSWORD: v.pipe(v.string(), v.nonEmpty("KINTONE_PASSWORD is required")),
758
- KINTONE_APP_ID: v.pipe(v.string(), v.nonEmpty("KINTONE_APP_ID is required")),
759
- SCHEMA_FILE_PATH: v.optional(v.string(), "schema.yaml")
760
- });
761
- const kintoneArgs = {
762
- domain: {
763
- type: "string",
764
- short: "d",
765
- description: "kintone domain (overrides KINTONE_DOMAIN env var)"
766
- },
767
- username: {
768
- type: "string",
769
- short: "u",
770
- description: "kintone username (overrides KINTONE_USERNAME env var)"
771
- },
772
- password: {
773
- type: "string",
774
- short: "p",
775
- description: "kintone password (overrides KINTONE_PASSWORD env var)"
776
- },
777
- "app-id": {
778
- type: "string",
779
- short: "a",
780
- description: "kintone app ID (overrides KINTONE_APP_ID env var)"
781
- },
782
- "schema-file": {
783
- type: "string",
784
- short: "f",
785
- description: "Schema file path (default: schema.yaml)"
786
- }
787
- };
788
- function resolveConfig(cliValues) {
789
- const result = v.safeParse(CliConfigSchema, {
790
- KINTONE_DOMAIN: cliValues.domain ?? process.env.KINTONE_DOMAIN ?? "",
791
- KINTONE_USERNAME: cliValues.username ?? process.env.KINTONE_USERNAME ?? "",
792
- KINTONE_PASSWORD: cliValues.password ?? process.env.KINTONE_PASSWORD ?? "",
793
- KINTONE_APP_ID: cliValues["app-id"] ?? process.env.KINTONE_APP_ID ?? "",
794
- SCHEMA_FILE_PATH: cliValues["schema-file"] ?? process.env.SCHEMA_FILE_PATH
795
- });
796
- if (!result.success) {
797
- const missing = result.issues.map((issue) => issue.message).join("\n ");
798
- throw new Error(`Missing required configuration:\n ${missing}`);
799
- }
800
- return {
801
- baseUrl: `https://${result.output.KINTONE_DOMAIN}`,
802
- username: result.output.KINTONE_USERNAME,
803
- password: result.output.KINTONE_PASSWORD,
804
- appId: result.output.KINTONE_APP_ID,
805
- schemaFilePath: result.output.SCHEMA_FILE_PATH
806
- };
807
- }
808
-
809
833
  //#endregion
810
834
  //#region src/cli/handleError.ts
811
835
  function handleCliError(error) {
@@ -1492,10 +1516,7 @@ var dump_default = define({
1492
1516
  const config = resolveConfig(ctx.values);
1493
1517
  const client = new KintoneRestAPIClient({
1494
1518
  baseUrl: config.baseUrl,
1495
- auth: {
1496
- username: config.username,
1497
- password: config.password
1498
- }
1519
+ auth: buildKintoneAuth(config.auth)
1499
1520
  });
1500
1521
  const s = p.spinner();
1501
1522
  s.start("Fetching form fields and layout...");
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "kintone-migrator",
3
- "version": "0.1.2",
3
+ "version": "0.2.0",
4
4
  "description": "kintone form schema migration tool",
5
5
  "license": "MIT",
6
6
  "author": "Hikaru Otabe",
@@ -53,10 +53,15 @@
53
53
  },
54
54
  "devDependencies": {
55
55
  "@biomejs/biome": "^2.3.14",
56
+ "@semantic-release/commit-analyzer": "^13.0.1",
57
+ "@semantic-release/github": "^12.0.5",
58
+ "@semantic-release/npm": "^13.1.4",
59
+ "@semantic-release/release-notes-generator": "^14.1.0",
56
60
  "@types/node": "^25.2.3",
57
61
  "@typescript/native-preview": "7.0.0-dev.20260211.1",
58
62
  "@vitest/coverage-v8": "^4.0.18",
59
63
  "dotenv-cli": "^11.0.0",
64
+ "semantic-release": "^25.0.3",
60
65
  "tsdown": "^0.20.3",
61
66
  "tsx": "^4.21.0",
62
67
  "typescript": "~5.9.3",