create-dovite 2.0.0 → 2.0.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/package.json CHANGED
@@ -1,13 +1,14 @@
1
1
  {
2
2
  "name": "create-dovite",
3
- "version": "2.0.0",
3
+ "version": "2.0.1",
4
4
  "description": "Vite template featuring Tailwind (v4), ShadCN (Canary), and DOMO integration.",
5
5
  "main": "index.js",
6
6
  "bin": {
7
7
  "create-dovite": "index.js"
8
8
  },
9
9
  "files": [
10
- "template",
10
+ "templates",
11
+ "src",
11
12
  "index.js"
12
13
  ],
13
14
  "keywords": [
package/src/files.js ADDED
@@ -0,0 +1,72 @@
1
+ const fs = require("fs");
2
+ const path = require("path");
3
+
4
+ function copyTemplateFiles(projectName, templateType) {
5
+ // __dirname is .../src
6
+ // templates are in .../templates
7
+ const templateDir = path.join(__dirname, "..", "templates", templateType);
8
+ const destDir = projectName; // Relative to CWD
9
+
10
+ if (fs.existsSync(templateDir)) {
11
+ console.log(`Copying ${templateType} template files...`);
12
+ const copyRecursive = (src, dest) => {
13
+ if (fs.statSync(src).isDirectory()) {
14
+ if (!fs.existsSync(dest)) {
15
+ fs.mkdirSync(dest, { recursive: true });
16
+ }
17
+ const files = fs.readdirSync(src);
18
+ for (const file of files) {
19
+ copyRecursive(path.join(src, file), path.join(dest, file));
20
+ }
21
+ } else {
22
+ fs.copyFileSync(src, dest);
23
+ }
24
+ };
25
+ copyRecursive(templateDir, destDir);
26
+ } else {
27
+ console.warn(`Template directory not found: ${templateDir}`);
28
+ }
29
+ }
30
+
31
+ function updateManifest(projectName) {
32
+ const publicDir = path.join(projectName, "public");
33
+ const manifestJsPath = path.join(publicDir, "manifest.js");
34
+ const manifestJsonPath = path.join(publicDir, "manifest.json");
35
+
36
+ if (fs.existsSync(manifestJsPath)) {
37
+ // Legacy/JS template handling
38
+ console.log("Updating manifest.js with project name...");
39
+ let manifestContent = fs.readFileSync(manifestJsPath, "utf8");
40
+ manifestContent = manifestContent.replace(
41
+ /name:\s*["']([^"']*)["']/g,
42
+ `name: "${projectName}"`
43
+ );
44
+ fs.writeFileSync(manifestJsPath, manifestContent);
45
+ } else if (fs.existsSync(manifestJsonPath)) {
46
+ // TS/JSON template handling
47
+ console.log("Updating manifest.json with project name...");
48
+ const manifestContent = JSON.parse(
49
+ fs.readFileSync(manifestJsonPath, "utf8")
50
+ );
51
+ manifestContent.name = projectName;
52
+ fs.writeFileSync(
53
+ manifestJsonPath,
54
+ JSON.stringify(manifestContent, null, 2)
55
+ );
56
+ } else {
57
+ // Create if missing (fallback)
58
+ if (!fs.existsSync(publicDir)) {
59
+ fs.mkdirSync(publicDir, { recursive: true });
60
+ }
61
+ // Default to JSON for new setup
62
+ console.log("Creating manifest.json with project name...");
63
+ const basicManifest = {
64
+ name: projectName,
65
+ version: "1.0.0",
66
+ description: `${projectName} application`,
67
+ };
68
+ fs.writeFileSync(manifestJsonPath, JSON.stringify(basicManifest, null, 2));
69
+ }
70
+ }
71
+
72
+ module.exports = { copyTemplateFiles, updateManifest };
package/src/prompts.js ADDED
@@ -0,0 +1,49 @@
1
+ const prompts = require("prompts");
2
+
3
+ async function getProjectDetails(initialProjectName) {
4
+ let projectName = initialProjectName;
5
+ let templateType = "react-js"; // default
6
+
7
+ const questions = [];
8
+
9
+ if (!projectName) {
10
+ questions.push({
11
+ type: "text",
12
+ name: "projectName",
13
+ message: "Project name:",
14
+ initial: "my-dovite-app",
15
+ });
16
+ }
17
+
18
+ questions.push({
19
+ type: "select",
20
+ name: "template",
21
+ message: "Select a template:",
22
+ choices: [
23
+ { title: "React JavaScript", value: "react-js" },
24
+ { title: "React TypeScript", value: "react-ts" },
25
+ ],
26
+ initial: 0,
27
+ });
28
+
29
+ if (questions.length > 0) {
30
+ const response = await prompts(questions, {
31
+ onCancel: () => {
32
+ console.log("Operation cancelled");
33
+ process.exit(0);
34
+ },
35
+ });
36
+
37
+ if (!projectName) projectName = response.projectName || projectName;
38
+ templateType = response.template;
39
+ }
40
+
41
+ if (!projectName) {
42
+ console.error("Please specify a project name");
43
+ process.exit(1);
44
+ }
45
+
46
+ return { projectName, templateType };
47
+ }
48
+
49
+ module.exports = { getProjectDetails };
package/src/setup.js ADDED
@@ -0,0 +1,106 @@
1
+ const { execSync } = require("child_process");
2
+ const fs = require("fs");
3
+ const path = require("path");
4
+
5
+ function createViteProject(projectName, templateType) {
6
+ console.log(
7
+ `Creating new project: ${projectName} with template ${templateType}`
8
+ );
9
+
10
+ const viteTemplate = templateType === "react-ts" ? "react-ts" : "react";
11
+ execSync(
12
+ `yarn create vite ${projectName} --template ${viteTemplate} --no-interactive`,
13
+ {
14
+ stdio: "inherit",
15
+ }
16
+ );
17
+ }
18
+
19
+ function updatePackageJson(projectName, templateType) {
20
+ console.log("Updating package name and scripts...");
21
+ const packageJsonPath = path.join(projectName, "package.json");
22
+ const packageJson = JSON.parse(fs.readFileSync(packageJsonPath, "utf8"));
23
+
24
+ packageJson.name = projectName;
25
+
26
+ packageJson.scripts = {
27
+ ...packageJson.scripts,
28
+ dev: "vite",
29
+ build: templateType === "react-ts" ? "tsc -b && vite build" : "vite build",
30
+ lint: "eslint .",
31
+ preview: "vite preview",
32
+ upload: "yarn run build && cd dist && domo publish && cd ..",
33
+ };
34
+
35
+ fs.writeFileSync(packageJsonPath, JSON.stringify(packageJson, null, 2));
36
+ }
37
+
38
+ function installDependencies(projectName) {
39
+ console.log("Installing dependencies...");
40
+ // We need to run this inside the project directory
41
+ // But since we are passing projectName, we can use cwd option or chdir before calling this.
42
+ // However, the original script chdir'd into the project.
43
+ // Let's assume the caller will handle chdir or we pass cwd.
44
+ // To keep it simple and consistent with original flow, let's assume we are IN the project dir
45
+ // OR we pass the cwd to execSync.
46
+ // The original script did `process.chdir(projectName)`.
47
+
48
+ // Let's stick to the original flow where we chdir in the main script,
49
+ // OR we can make these functions robust.
50
+ // For now, let's assume we are inside the directory for these commands to work easily
51
+ // without passing cwd everywhere, BUT `updatePackageJson` used `path.join`.
52
+ // Let's make `updatePackageJson` work with relative path, and these commands too.
53
+
54
+ // Actually, `yarn` needs to run in the project dir.
55
+
56
+ const options = { stdio: "inherit", cwd: projectName };
57
+
58
+ execSync("yarn", options);
59
+
60
+ console.log("Installing additional dependencies...");
61
+ execSync(
62
+ "yarn add tailwindcss @tailwindcss/vite @domoinc/ryuu-proxy ryuu.js tailwind-merge react-icons",
63
+ options
64
+ );
65
+ execSync("yarn add -D @types/node", options);
66
+ }
67
+
68
+ function initializeShadcn(projectName) {
69
+ console.log("Initializing shadcn...");
70
+ const options = { stdio: "inherit", cwd: projectName };
71
+ try {
72
+ execSync("npx shadcn@latest init", options);
73
+
74
+ // Install new dependencies after shadcn (it might add some)
75
+ // The original script ran yarn again.
76
+ console.log("Installing final dependencies...");
77
+ execSync("yarn", options);
78
+
79
+ execSync("npx shadcn@latest add button", options);
80
+ } catch (error) {
81
+ console.log(
82
+ 'Note: You may need to run "npx shadcn@latest init" manually if initialization failed.'
83
+ );
84
+ }
85
+ }
86
+
87
+ function initializeGit(projectName) {
88
+ console.log("Initializing git");
89
+ const options = { stdio: "inherit", cwd: projectName };
90
+ try {
91
+ execSync("git init", options);
92
+ execSync("git add .", options);
93
+ execSync(`git commit -m "first commit"`, options);
94
+ execSync("git checkout -b main", options);
95
+ } catch (e) {
96
+ console.log("Git initialization failed or skipped.");
97
+ }
98
+ }
99
+
100
+ module.exports = {
101
+ createViteProject,
102
+ updatePackageJson,
103
+ installDependencies,
104
+ initializeShadcn,
105
+ initializeGit,
106
+ };
@@ -0,0 +1,7 @@
1
+ {
2
+ "compilerOptions": {
3
+ "paths": {
4
+ "@/*": ["./src/*"]
5
+ }
6
+ }
7
+ }
@@ -0,0 +1,12 @@
1
+ {
2
+ "name": "project-name",
3
+ "version": "0.0.1",
4
+ "size": {
5
+ "width": 3,
6
+ "height": 3
7
+ },
8
+ "mapping": [],
9
+ "collections": [],
10
+ "workflowMapping": [],
11
+ "packagesMapping": []
12
+ }
@@ -0,0 +1,56 @@
1
+ /* eslint-disable react/prop-types */
2
+ import { createContext, useState, useEffect } from "react";
3
+ import DomoApi from "./DomoAPI";
4
+
5
+ export const UserContext = createContext();
6
+
7
+ export const UserProvider = ({ children }) => {
8
+ const [currentUser, setCurrentUser] = useState("");
9
+ const [currentUserId, setCurrentUserId] = useState("");
10
+ const [avatarKey, setAvatarKey] = useState("");
11
+ const [customer, setCustomer] = useState("");
12
+ const [host, setHost] = useState("");
13
+
14
+ useEffect(() => {
15
+ let isUserFetched = false;
16
+
17
+ DomoApi.GetCurrentUser().then((data) => {
18
+ // console.log("User Data",data);
19
+
20
+ if (!isUserFetched) {
21
+ const userId = data?.userId;
22
+ const displayName = data?.displayName;
23
+ const avatarKey = data?.avatarKey;
24
+ const customer=data?.customer;
25
+ const host=data?.host;
26
+
27
+ setCurrentUser(displayName || "");
28
+ setCurrentUserId(userId || "");
29
+ setAvatarKey(avatarKey || "");
30
+ setCustomer(customer || "");
31
+ setHost(host || "");
32
+
33
+
34
+ isUserFetched = true;
35
+ }
36
+ });
37
+
38
+ return () => {
39
+ isUserFetched = true;
40
+ };
41
+ }, []);
42
+
43
+ return (
44
+ <UserContext.Provider
45
+ value={{
46
+ currentUser,
47
+ currentUserId,
48
+ avatarKey,
49
+ customer,
50
+ host
51
+ }}
52
+ >
53
+ {children}
54
+ </UserContext.Provider>
55
+ );
56
+ };
@@ -0,0 +1,235 @@
1
+ import domo from "ryuu.js";
2
+ import axios from "axios";
3
+
4
+ export async function fetchAIData(prompt, template, maxWords) {
5
+ try {
6
+ // Validate the required "prompt" parameter
7
+ if (!prompt || typeof prompt !== "string") {
8
+ throw new Error("The 'prompt' parameter is required and must be a string.");
9
+ }
10
+
11
+ // Construct the body dynamically, including properties only if they are valid
12
+ const body = {
13
+ input: prompt,
14
+ ...(template && typeof template === "string" && {
15
+ promptTemplate: {
16
+ template,
17
+ },
18
+ }),
19
+ ...(maxWords && !isNaN(maxWords) && {
20
+ parameters: {
21
+ max_words: maxWords.toString(),
22
+ },
23
+ }),
24
+ };
25
+
26
+ // Send the POST request
27
+ const response = await domo.post(`/domo/ai/v1/text/generation`, body);
28
+ console.log("AI Response:", response.output);
29
+
30
+ return response?.output;
31
+ } catch (error) {
32
+ console.error("Error fetching data:", error);
33
+ throw error; // Re-throw the error for better upstream handling
34
+ }
35
+ }
36
+
37
+
38
+ export async function fetchData(dataset) {
39
+ try {
40
+ const response = await domo.get(`/data/v1/${dataset}`).then((data) => {
41
+ return data;
42
+ });
43
+ // console.log(response);
44
+ return response;
45
+ } catch (error) {
46
+ console.error("Error fetching data:", error);
47
+ }
48
+ }
49
+
50
+ export async function fetchSqlData(dataset, query) {
51
+ // console.log("Query",query);
52
+
53
+ // Ensure the query is a string
54
+ if (typeof query !== "string") {
55
+ throw new Error("Query must be a string");
56
+ }
57
+
58
+ try {
59
+ // Fetch data from the API
60
+ const apiData = await domo
61
+ .post(`/sql/v1/${dataset}`, query, { contentType: "text/plain" })
62
+ .then((data) => {
63
+ // console.log('Fetched Data:', data);
64
+ return data;
65
+ });
66
+
67
+ // Validate the fetched data
68
+ if (!apiData || !apiData.columns || !apiData.rows) {
69
+ throw new Error("Invalid data received from the API");
70
+ }
71
+
72
+ // Extract and clean column names
73
+ const cleanedColumns = apiData.columns.map((column) => {
74
+ return column
75
+ .replace(/`/g, "")
76
+ .replace(/T1\./g, "")
77
+ .replace(/avg\((.*?)\)/i, "$1")
78
+ .trim();
79
+ });
80
+
81
+ // Map rows to cleaned column names
82
+ const jsonResult = apiData.rows.map((row) => {
83
+ const jsonObject = {};
84
+ cleanedColumns.forEach((cleanedColumn, index) => {
85
+ jsonObject[cleanedColumn] = row[index];
86
+ });
87
+ return jsonObject;
88
+ });
89
+
90
+ // console.log("Mapped SQL DATA",jsonResult);
91
+
92
+ // Return the dynamically created JSON
93
+ return jsonResult;
94
+ } catch (error) {
95
+ console.error("Error fetching or processing data:", error);
96
+ throw error; // Rethrow the error for the caller to handle
97
+ }
98
+ }
99
+
100
+ export async function sendEmail(to, subject, body, attachment) {
101
+ const data = {
102
+ to,
103
+ subject,
104
+ body,
105
+ ...(attachment && { attachment: [attachment] }),
106
+ };
107
+
108
+ if (data) {
109
+ try {
110
+ const response = await domo.post(
111
+ `/domo/workflow/v1/models/email/start`,
112
+ data
113
+ );
114
+ if (response) {
115
+ console.log("response", response);
116
+ }
117
+ } catch (err) {
118
+ console.error("Error sending email:", err);
119
+ }
120
+ }
121
+ }
122
+
123
+ //Dataflow
124
+ export const DataflowsActions = async (action, dataflowId) => {
125
+ const data = {
126
+ action,
127
+ dataflowId,
128
+ result: true,
129
+ };
130
+
131
+ if (data) {
132
+ try {
133
+ const response = await domo.post(
134
+ `/domo/workflow/v1/models/dataflow/start`,
135
+ data
136
+ );
137
+ if (response) {
138
+ console.log("response", response);
139
+ }
140
+ } catch (err) {
141
+ console.error("Error sending email:", err);
142
+ }
143
+ }
144
+ };
145
+ export const generateAccessToken = async (clientId, clientSecret) => {
146
+ const tokenUrl = "https://api.domo.com/oauth/token";
147
+ try {
148
+ const response = await axios.post(
149
+ tokenUrl,
150
+ new URLSearchParams({
151
+ grant_type: "client_credentials",
152
+ scope: "user",
153
+ }).toString(),
154
+ {
155
+ headers: {
156
+ "Content-Type": "application/x-www-form-urlencoded",
157
+ },
158
+ auth: {
159
+ username: clientId,
160
+ password: clientSecret,
161
+ },
162
+ }
163
+ );
164
+ console.log("Response:", response);
165
+
166
+ console.log("Access Token:", response.data.access_token);
167
+
168
+ return response.data.access_token;
169
+ } catch (err) {
170
+ console.error("Error:", err);
171
+ throw err;
172
+ }
173
+ };
174
+
175
+ //List Of Users
176
+ export const fetchUsers = async (accessToken) => {
177
+ const userUrl = `https://api.domo.com/v1/users?limit=500`;
178
+ console.log("accessToken", accessToken);
179
+ try {
180
+ if (!accessToken) {
181
+ console.log("Access token not found");
182
+ return;
183
+ }
184
+ const response = await axios.get(userUrl, {
185
+ headers: {
186
+ Authorization: `Bearer ${accessToken}`,
187
+ },
188
+ });
189
+ console.log("List of users with access token", response.data);
190
+ return response.data;
191
+ } catch (err) {
192
+ console.error("Error fetching User details:", err);
193
+ }
194
+ };
195
+
196
+ //List Of Dataset
197
+ export const fetchDatasets = async (accessToken) => {
198
+ const datasetUrl = `https://api.domo.com/v1/datasets`;
199
+
200
+ try {
201
+ if (!accessToken) {
202
+ await generateAccessToken();
203
+ }
204
+ const response = await axios.get(datasetUrl, {
205
+ headers: {
206
+ Authorization: `Bearer ${accessToken}`,
207
+ },
208
+ });
209
+ // console.log("List of dataset", response.data);
210
+ return response.data;
211
+ } catch (err) {
212
+ console.error("Error fetching dataset details:", err);
213
+ }
214
+ };
215
+
216
+ //Perticaular Dataset Details
217
+ export const fetchDatasetDetails = async (accessToken, datasetId) => {
218
+ const datasetUrl = `https://api.domo.com/v1/datasets/${datasetId}`;
219
+
220
+ try {
221
+ if (!accessToken) {
222
+ await generateAccessToken();
223
+ }
224
+
225
+ const response = await axios.get(datasetUrl, {
226
+ headers: {
227
+ Authorization: `Bearer ${accessToken}`,
228
+ },
229
+ });
230
+ // console.log("data", response.data)
231
+ return response.data;
232
+ } catch (err) {
233
+ console.error("Error fetching dataset details:", err);
234
+ }
235
+ };