gims 0.4.2

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 +150 -0
  2. package/bin/gims.js +167 -0
  3. package/package.json +44 -0
package/README.md ADDED
@@ -0,0 +1,150 @@
1
+ Here’s a **complete usage guide** for `gims` (Git Made Simple) CLI tool:
2
+
3
+ ---
4
+
5
+ ## πŸš€ Installation
6
+
7
+ ```bash
8
+ npm install -g gims
9
+ ```
10
+
11
+ This installs the `gims` command and a shortcut alias:
12
+
13
+ ```bash
14
+ g # shortcut for gims
15
+ ```
16
+
17
+ ---
18
+
19
+ ## πŸ”§ Environment Setup (Optional for AI)
20
+
21
+ To enable AI-generated commit messages:
22
+
23
+ ### βœ… Option 1: Gemini API
24
+
25
+ ```bash
26
+ export GEMINI_API_KEY='your_gemini_api_key'
27
+ ```
28
+
29
+ ### βœ… Option 2: OpenAI API (used if Gemini key not found)
30
+
31
+ ```bash
32
+ export OPENAI_API_KEY='your_openai_api_key'
33
+ ```
34
+
35
+ If neither is set, it defaults to a generic commit message.
36
+
37
+ ---
38
+
39
+ ## 🧠 AI Commit Modes
40
+
41
+ ### 1. Commit Locally with AI Message
42
+
43
+ ```bash
44
+ g l # or gims local
45
+ ```
46
+
47
+ β†’ Adds and commits current changes locally with a descriptive commit message generated by AI.
48
+
49
+ ### 2. Commit & Push with AI Message
50
+
51
+ ```bash
52
+ g o # or gims online
53
+ ```
54
+
55
+ β†’ Adds, commits, and pushes the current changes to the remote branch.
56
+
57
+ ---
58
+
59
+ ## πŸ“š Version History Navigation
60
+
61
+ ### View Git Logs (Short)
62
+
63
+ ```bash
64
+ g ls # or gims list
65
+ ```
66
+
67
+ β†’ Shows a numbered short log:
68
+
69
+ ```
70
+ 1. 1234abc Added login feature
71
+ 2. 5678def Fixed bug in auth flow
72
+ ```
73
+
74
+ ### View Git Logs (Full)
75
+
76
+ ```bash
77
+ g ll # or gims largelist
78
+ ```
79
+
80
+ β†’ Full `git log` (without pager).
81
+
82
+ ---
83
+
84
+ ## 🌿 Branching & Resetting
85
+
86
+ ### Create Branch from a Commit or Number
87
+
88
+ ```bash
89
+ g b 2 try-new-idea
90
+ ```
91
+
92
+ β†’ Branches off from commit #2 (resolved via `g ls`) into a new branch `try-new-idea`.
93
+
94
+ ### Reset to a Commit or Number
95
+
96
+ ```bash
97
+ g r 1 --hard
98
+ ```
99
+
100
+ β†’ Resets the current branch to commit #1 permanently (`--hard` is optional).
101
+
102
+ ### Revert a Commit or Number
103
+
104
+ ```bash
105
+ g rv 3
106
+ ```
107
+
108
+ β†’ Reverts changes made by commit #3 (safe, non-destructive).
109
+
110
+ ---
111
+
112
+ ## πŸ†• Git Init
113
+
114
+ ```bash
115
+ g i # or gims init
116
+ ```
117
+
118
+ β†’ Initializes a new Git repository.
119
+
120
+ ---
121
+
122
+ ## πŸ“ Example Workflow
123
+
124
+ ```bash
125
+ cd myproject/
126
+ g i # Initialize repository
127
+ touch index.js # Add file
128
+ g l # Auto commit locally with AI
129
+ g ls # See commit history
130
+ g b 1 try-feature # Branch out from earlier version
131
+ ```
132
+
133
+ ---
134
+
135
+ ## πŸ“¦ Dependencies Used
136
+
137
+ * [`simple-git`](https://www.npmjs.com/package/simple-git) – Git CLI wrapper
138
+ * [`openai`](https://www.npmjs.com/package/openai) – OpenAI SDK
139
+ * [`@google-ai/gemini`](https://www.npmjs.com/package/@google-ai/gemini) – Gemini SDK
140
+ * [`commander`](https://www.npmjs.com/package/commander) – CLI argument parser
141
+
142
+ ---
143
+
144
+ Let me know if you’d like to:
145
+
146
+ * Add auto-push branch creation
147
+ * Show full diff preview
148
+ * Add emojis, scopes, or conventional commits
149
+ * Bundle this as a GUI as well!
150
+
package/bin/gims.js ADDED
@@ -0,0 +1,167 @@
1
+ #!/usr/bin/env node
2
+
3
+ /*
4
+ gims (Git Made Simple) CLI
5
+ Features:
6
+ - Initialize repository (init alias: i)
7
+ - Auto commit with AI-generated messages (Gemini or OpenAI)
8
+ Modes:
9
+ * local (alias: l)
10
+ * online (alias: o)
11
+ - Navigation:
12
+ * list (alias: ls): numbered git log --oneline
13
+ * largelist (alias: ll): full git log --no-pager
14
+ * branch <commit|#> [name] (alias: b)
15
+ * reset <commit|#> [--hard] (alias: r)
16
+ * revert <commit|#> (alias: rv)
17
+
18
+ Env vars:
19
+ - GEMINI_API_KEY: use Google Gemini API
20
+ - OPENAI_API_KEY: fallback to OpenAI if Gemini not set
21
+ - none: fallback to generic commit messages
22
+
23
+ Usage:
24
+ npm install -g gims
25
+ export GEMINI_API_KEY=...
26
+ export OPENAI_API_KEY=...
27
+ gims init # or g i
28
+ gims local # or g l
29
+ */
30
+
31
+ const { Command } = require('commander');
32
+ const simpleGit = require('simple-git');
33
+ const process = require('process');
34
+ const { OpenAI } = require('openai');
35
+ const { GoogleGenAI } = require('@google/genai');
36
+
37
+ const program = new Command();
38
+ const git = simpleGit();
39
+
40
+ // Setup AI clients
41
+ const hasGemini = !!process.env.GEMINI_API_KEY;
42
+ const hasOpenAI = !hasGemini && !!process.env.OPENAI_API_KEY;
43
+ let genai, openai;
44
+
45
+ if (hasGemini) {
46
+ genai = new GoogleGenAI({ apiKey: process.env.GEMINI_API_KEY });
47
+ } else if (hasOpenAI) {
48
+ openai = new OpenAI({ apiKey: process.env.OPENAI_API_KEY });
49
+ }
50
+
51
+ async function generateCommitMessage(diff) {
52
+ if (hasGemini) {
53
+ const res = await genai.models.generateContent({
54
+ model: 'gemini-2.0-flash',
55
+ contents: `Write a concise git commit message for these changes:\n${diff}`,
56
+ });
57
+ return res.text.trim();
58
+ }
59
+
60
+ if (hasOpenAI) {
61
+ const res = await openai.chat.completions.create({
62
+ model: 'gpt-4o-mini',
63
+ messages: [{ role: 'user', content: `Write a concise git commit message for these changes:\n${diff}` }],
64
+ temperature: 0.5,
65
+ });
66
+ return res.choices[0].message.content.trim();
67
+ }
68
+
69
+ // fallback generic
70
+ return 'Update project code';
71
+ }
72
+
73
+ async function resolveCommit(input) {
74
+ if (/^\d+$/.test(input)) {
75
+ const { all } = await git.log();
76
+ const idx = parseInt(input, 10) - 1;
77
+ if (idx < 0 || idx >= all.length) throw new Error('Index out of range');
78
+ return all[idx].hash;
79
+ }
80
+ return input;
81
+ }
82
+
83
+ program.name('gims').alias('g').version('0.4.2');
84
+
85
+ program.command('init').alias('i')
86
+ .description('Initialize a new Git repository')
87
+ .action(async () => {
88
+ await git.init();
89
+ console.log('Initialized repo.');
90
+ });
91
+
92
+ // Local commit: stage all, get staged diff, AI message, commit
93
+ program.command('local').alias('l')
94
+ .description('AI-powered local commit')
95
+ .action(async () => {
96
+ // stage all changes first
97
+ await git.add('.');
98
+ // get diff of staged changes
99
+ const diff = await git.diff(['--cached']);
100
+ if (!diff) return console.log('No changes to commit.');
101
+ console.log('Generating commit message...');
102
+ const msg = await generateCommitMessage(diff);
103
+ await git.commit(msg);
104
+ console.log(`Committed locally: "${msg}"`);
105
+ });
106
+
107
+ // Online commit: stage, diff, message, commit, push
108
+ program.command('online').alias('o')
109
+ .description('AI commit + push')
110
+ .action(async () => {
111
+ await git.add('.');
112
+ const diff = await git.diff(['--cached']);
113
+ if (!diff) return console.log('No changes to commit.');
114
+ console.log('Generating commit message...');
115
+ const msg = await generateCommitMessage(diff);
116
+ await git.commit(msg);
117
+ await git.push();
118
+ console.log(`Committed & pushed: "${msg}"`);
119
+ });
120
+
121
+ program.command('list').alias('ls')
122
+ .description('Short numbered git log')
123
+ .action(async () => {
124
+ const { all } = await git.log();
125
+ all.forEach((c, i) => console.log(`${i+1}. ${c.hash.slice(0,7)} ${c.message}`));
126
+ });
127
+
128
+ program.command('largelist').alias('ll')
129
+ .description('Full git log without pager')
130
+ .action(async () => {
131
+ console.log(await git.raw(['--no-pager', 'log']));
132
+ });
133
+
134
+ program.command('branch <c> [name]').alias('b')
135
+ .description('Branch from commit/index')
136
+ .action(async (c, name) => {
137
+ try {
138
+ const sha = await resolveCommit(c);
139
+ const br = name || `branch-${sha.slice(0,7)}`;
140
+ await git.checkout(['-b', br, sha]);
141
+ console.log(`Switched to branch ${br} at ${sha}`);
142
+ } catch (e) { console.error(e.message); }
143
+ });
144
+
145
+ program.command('reset <c>').alias('r')
146
+ .description('Reset branch to commit/index')
147
+ .option('--hard', 'hard reset')
148
+ .action(async (c, opts) => {
149
+ try {
150
+ const sha = await resolveCommit(c);
151
+ const mode = opts.hard ? '--hard' : '--soft';
152
+ await git.raw(['reset', mode, sha]);
153
+ console.log(`Reset (${mode}) to ${sha}`);
154
+ } catch (e) { console.error(e.message); }
155
+ });
156
+
157
+ program.command('revert <c>').alias('rv')
158
+ .description('Revert commit/index safely')
159
+ .action(async (c) => {
160
+ try {
161
+ const sha = await resolveCommit(c);
162
+ await git.revert(sha);
163
+ console.log(`Reverted ${sha}`);
164
+ } catch (e) { console.error(e.message); }
165
+ });
166
+
167
+ program.parse(process.argv);
package/package.json ADDED
@@ -0,0 +1,44 @@
1
+ {
2
+ "name": "gims",
3
+ "version": "0.4.2",
4
+ "description": "Git Made Simple – AI‑powered git helper using Gemini / OpenAI",
5
+ "author": "S41R4J",
6
+ "license": "MIT",
7
+ "bin": {
8
+ "gims": "bin/gims.js",
9
+ "g": "bin/gims.js"
10
+ },
11
+ "keywords": [
12
+ "git",
13
+ "cli",
14
+ "ai",
15
+ "commit",
16
+ "gpt",
17
+ "gemini",
18
+ "openai",
19
+ "developer-tools",
20
+ "version-control"
21
+ ],
22
+ "repository": {
23
+ "type": "git",
24
+ "url": "git+https://github.com/s41r4j/gims.git"
25
+ },
26
+ "bugs": {
27
+ "url": "https://github.com/s41r4j/gims/issues"
28
+ },
29
+ "homepage": "https://github.com/s41r4j/gims#readme",
30
+ "main": "bin/gims.js",
31
+ "engines": {
32
+ "node": ">=20.0.0"
33
+ },
34
+ "dependencies": {
35
+ "@google/genai": "^1.5.1",
36
+ "commander": "^11.1.0",
37
+ "openai": "^4.0.0",
38
+ "simple-git": "^3.19.1"
39
+ },
40
+ "type": "commonjs",
41
+ "scripts": {
42
+ "test": "echo \"No tests yet\" && exit 0"
43
+ }
44
+ }