@famgia/omnify-laravel 0.0.88 → 0.0.90
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/dist/{chunk-YVVAJA3T.js → chunk-2QSKZS63.js} +188 -12
- package/dist/chunk-2QSKZS63.js.map +1 -0
- package/dist/index.cjs +190 -11
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +48 -1
- package/dist/index.d.ts +48 -1
- package/dist/index.js +5 -1
- package/dist/plugin.cjs +186 -11
- package/dist/plugin.cjs.map +1 -1
- package/dist/plugin.js +1 -1
- package/package.json +5 -5
- package/scripts/postinstall.js +29 -36
- package/stubs/ai-guides/README.md.stub +95 -0
- package/stubs/ai-guides/claude-agents/architect.md.stub +150 -0
- package/stubs/ai-guides/claude-agents/developer.md.stub +190 -0
- package/stubs/ai-guides/claude-agents/reviewer.md.stub +134 -0
- package/stubs/ai-guides/claude-agents/tester.md.stub +196 -0
- package/stubs/ai-guides/claude-checklists/backend.md.stub +112 -0
- package/stubs/ai-guides/claude-omnify/antdesign-guide.md.stub +401 -0
- package/stubs/ai-guides/claude-omnify/config-guide.md.stub +253 -0
- package/stubs/ai-guides/claude-omnify/japan-guide.md.stub +186 -0
- package/stubs/ai-guides/claude-omnify/laravel-guide.md.stub +61 -0
- package/stubs/ai-guides/claude-omnify/react-form-guide.md.stub +259 -0
- package/stubs/ai-guides/claude-omnify/schema-guide.md.stub +115 -0
- package/stubs/ai-guides/claude-omnify/typescript-guide.md.stub +310 -0
- package/stubs/ai-guides/claude-rules/naming.md.stub +364 -0
- package/stubs/ai-guides/claude-rules/performance.md.stub +251 -0
- package/stubs/ai-guides/claude-rules/security.md.stub +159 -0
- package/stubs/ai-guides/claude-workflows/bug-fix.md.stub +201 -0
- package/stubs/ai-guides/claude-workflows/code-review.md.stub +164 -0
- package/stubs/ai-guides/claude-workflows/new-feature.md.stub +327 -0
- package/stubs/ai-guides/cursor/laravel-controller.mdc.stub +391 -0
- package/stubs/ai-guides/cursor/laravel-request.mdc.stub +112 -0
- package/stubs/ai-guides/cursor/laravel-resource.mdc.stub +73 -0
- package/stubs/ai-guides/cursor/laravel-review.mdc.stub +69 -0
- package/stubs/ai-guides/cursor/laravel-testing.mdc.stub +138 -0
- package/stubs/ai-guides/cursor/laravel.mdc.stub +82 -0
- package/stubs/ai-guides/cursor/omnify.mdc.stub +58 -0
- package/stubs/ai-guides/laravel/README.md.stub +59 -0
- package/stubs/ai-guides/laravel/architecture.md.stub +424 -0
- package/stubs/ai-guides/laravel/controller.md.stub +484 -0
- package/stubs/ai-guides/laravel/datetime.md.stub +334 -0
- package/stubs/ai-guides/laravel/openapi.md.stub +369 -0
- package/stubs/ai-guides/laravel/request.md.stub +450 -0
- package/stubs/ai-guides/laravel/resource.md.stub +516 -0
- package/stubs/ai-guides/laravel/service.md.stub +503 -0
- package/stubs/ai-guides/laravel/testing.md.stub +1504 -0
- package/ai-guides/laravel-guide.md +0 -461
- package/dist/chunk-YVVAJA3T.js.map +0 -1
package/dist/index.cjs
CHANGED
|
@@ -24,6 +24,7 @@ __export(index_exports, {
|
|
|
24
24
|
formatForeignKey: () => formatForeignKey,
|
|
25
25
|
formatIndex: () => formatIndex,
|
|
26
26
|
formatMigrationFile: () => formatMigrationFile,
|
|
27
|
+
generateAIGuides: () => generateAIGuides,
|
|
27
28
|
generateAlterMigration: () => generateAlterMigration,
|
|
28
29
|
generateDropMigrationForTable: () => generateDropMigrationForTable,
|
|
29
30
|
generateDropTableMigration: () => generateDropTableMigration,
|
|
@@ -43,6 +44,7 @@ __export(index_exports, {
|
|
|
43
44
|
laravelPlugin: () => laravelPlugin,
|
|
44
45
|
propertyToColumnMethod: () => propertyToColumnMethod,
|
|
45
46
|
schemaToBlueprint: () => schemaToBlueprint,
|
|
47
|
+
shouldGenerateAIGuides: () => shouldGenerateAIGuides,
|
|
46
48
|
toColumnName: () => toColumnName,
|
|
47
49
|
toTableName: () => toTableName
|
|
48
50
|
});
|
|
@@ -2637,8 +2639,8 @@ function getFactoryPath(factory) {
|
|
|
2637
2639
|
}
|
|
2638
2640
|
|
|
2639
2641
|
// src/plugin.ts
|
|
2640
|
-
var
|
|
2641
|
-
var
|
|
2642
|
+
var import_node_fs2 = require("fs");
|
|
2643
|
+
var import_node_path2 = require("path");
|
|
2642
2644
|
|
|
2643
2645
|
// src/request/generator.ts
|
|
2644
2646
|
var import_omnify_types3 = require("@famgia/omnify-types");
|
|
@@ -3971,6 +3973,162 @@ function getResourcePath(resource) {
|
|
|
3971
3973
|
return resource.path;
|
|
3972
3974
|
}
|
|
3973
3975
|
|
|
3976
|
+
// src/ai-guides/generator.ts
|
|
3977
|
+
var import_node_fs = require("fs");
|
|
3978
|
+
var import_node_path = require("path");
|
|
3979
|
+
var import_node_url = require("url");
|
|
3980
|
+
var import_meta = {};
|
|
3981
|
+
var __filename = (0, import_node_url.fileURLToPath)(import_meta.url);
|
|
3982
|
+
var __dirname = (0, import_node_path.dirname)(__filename);
|
|
3983
|
+
function getStubsDir() {
|
|
3984
|
+
const devPath = (0, import_node_path.resolve)(__dirname, "../../stubs/ai-guides");
|
|
3985
|
+
if ((0, import_node_fs.existsSync)(devPath)) {
|
|
3986
|
+
return devPath;
|
|
3987
|
+
}
|
|
3988
|
+
const distPath = (0, import_node_path.resolve)(__dirname, "../stubs/ai-guides");
|
|
3989
|
+
if ((0, import_node_fs.existsSync)(distPath)) {
|
|
3990
|
+
return distPath;
|
|
3991
|
+
}
|
|
3992
|
+
throw new Error("AI guides stubs not found");
|
|
3993
|
+
}
|
|
3994
|
+
function extractLaravelBasePath(modelsPath) {
|
|
3995
|
+
if (!modelsPath) return "app";
|
|
3996
|
+
const normalized = modelsPath.replace(/\\/g, "/");
|
|
3997
|
+
const match = normalized.match(/^(.+?)\/Models(?:\/.*)?$/);
|
|
3998
|
+
if (match && match[1]) {
|
|
3999
|
+
return match[1];
|
|
4000
|
+
}
|
|
4001
|
+
const parts = normalized.split("/").filter(Boolean);
|
|
4002
|
+
if (parts.length > 1) {
|
|
4003
|
+
return parts.slice(0, -1).join("/");
|
|
4004
|
+
}
|
|
4005
|
+
return "app";
|
|
4006
|
+
}
|
|
4007
|
+
function replacePlaceholders(content, basePath) {
|
|
4008
|
+
return content.replace(/\{\{LARAVEL_BASE\}\}/g, basePath);
|
|
4009
|
+
}
|
|
4010
|
+
function copyStubs(srcDir, destDir, transform) {
|
|
4011
|
+
const writtenFiles = [];
|
|
4012
|
+
if (!(0, import_node_fs.existsSync)(srcDir)) {
|
|
4013
|
+
return writtenFiles;
|
|
4014
|
+
}
|
|
4015
|
+
if (!(0, import_node_fs.existsSync)(destDir)) {
|
|
4016
|
+
(0, import_node_fs.mkdirSync)(destDir, { recursive: true });
|
|
4017
|
+
}
|
|
4018
|
+
const entries = (0, import_node_fs.readdirSync)(srcDir, { withFileTypes: true });
|
|
4019
|
+
for (const entry of entries) {
|
|
4020
|
+
const srcPath = (0, import_node_path.join)(srcDir, entry.name);
|
|
4021
|
+
if (entry.isDirectory()) {
|
|
4022
|
+
const subDestDir = (0, import_node_path.join)(destDir, entry.name);
|
|
4023
|
+
const subFiles = copyStubs(srcPath, subDestDir, transform);
|
|
4024
|
+
writtenFiles.push(...subFiles);
|
|
4025
|
+
} else if (entry.isFile() && entry.name.endsWith(".stub")) {
|
|
4026
|
+
const destName = entry.name.slice(0, -5);
|
|
4027
|
+
const destPath = (0, import_node_path.join)(destDir, destName);
|
|
4028
|
+
let content = (0, import_node_fs.readFileSync)(srcPath, "utf-8");
|
|
4029
|
+
if (transform) {
|
|
4030
|
+
content = transform(content);
|
|
4031
|
+
}
|
|
4032
|
+
(0, import_node_fs.writeFileSync)(destPath, content);
|
|
4033
|
+
writtenFiles.push(destPath);
|
|
4034
|
+
}
|
|
4035
|
+
}
|
|
4036
|
+
return writtenFiles;
|
|
4037
|
+
}
|
|
4038
|
+
function generateAIGuides(rootDir, options = {}) {
|
|
4039
|
+
const stubsDir = getStubsDir();
|
|
4040
|
+
const basePath = options.laravelBasePath || extractLaravelBasePath(options.modelsPath);
|
|
4041
|
+
const result = {
|
|
4042
|
+
claudeGuides: 0,
|
|
4043
|
+
claudeRules: 0,
|
|
4044
|
+
claudeChecklists: 0,
|
|
4045
|
+
claudeWorkflows: 0,
|
|
4046
|
+
claudeAgents: 0,
|
|
4047
|
+
claudeOmnify: 0,
|
|
4048
|
+
cursorRules: 0,
|
|
4049
|
+
files: []
|
|
4050
|
+
};
|
|
4051
|
+
const readmeSrcPath = (0, import_node_path.join)(stubsDir, "README.md.stub");
|
|
4052
|
+
if ((0, import_node_fs.existsSync)(readmeSrcPath)) {
|
|
4053
|
+
const readmeDestDir = (0, import_node_path.resolve)(rootDir, ".claude/omnify");
|
|
4054
|
+
if (!(0, import_node_fs.existsSync)(readmeDestDir)) {
|
|
4055
|
+
(0, import_node_fs.mkdirSync)(readmeDestDir, { recursive: true });
|
|
4056
|
+
}
|
|
4057
|
+
const content = (0, import_node_fs.readFileSync)(readmeSrcPath, "utf-8");
|
|
4058
|
+
(0, import_node_fs.writeFileSync)((0, import_node_path.resolve)(readmeDestDir, "README.md"), content);
|
|
4059
|
+
result.files.push((0, import_node_path.resolve)(readmeDestDir, "README.md"));
|
|
4060
|
+
}
|
|
4061
|
+
const claudeSrcDir = (0, import_node_path.join)(stubsDir, "laravel");
|
|
4062
|
+
const claudeDestDir = (0, import_node_path.resolve)(rootDir, ".claude/omnify/guides/laravel");
|
|
4063
|
+
if ((0, import_node_fs.existsSync)(claudeSrcDir)) {
|
|
4064
|
+
const files = copyStubs(claudeSrcDir, claudeDestDir);
|
|
4065
|
+
result.claudeGuides = files.length;
|
|
4066
|
+
result.files.push(...files);
|
|
4067
|
+
}
|
|
4068
|
+
const claudeRulesSrcDir = (0, import_node_path.join)(stubsDir, "claude-rules");
|
|
4069
|
+
const claudeRulesDestDir = (0, import_node_path.resolve)(rootDir, ".claude/omnify/rules");
|
|
4070
|
+
if ((0, import_node_fs.existsSync)(claudeRulesSrcDir)) {
|
|
4071
|
+
const files = copyStubs(claudeRulesSrcDir, claudeRulesDestDir);
|
|
4072
|
+
result.claudeRules = files.length;
|
|
4073
|
+
result.files.push(...files);
|
|
4074
|
+
}
|
|
4075
|
+
const claudeChecklistsSrcDir = (0, import_node_path.join)(stubsDir, "claude-checklists");
|
|
4076
|
+
const claudeChecklistsDestDir = (0, import_node_path.resolve)(rootDir, ".claude/omnify/checklists");
|
|
4077
|
+
if ((0, import_node_fs.existsSync)(claudeChecklistsSrcDir)) {
|
|
4078
|
+
const files = copyStubs(claudeChecklistsSrcDir, claudeChecklistsDestDir);
|
|
4079
|
+
result.claudeChecklists = files.length;
|
|
4080
|
+
result.files.push(...files);
|
|
4081
|
+
}
|
|
4082
|
+
const claudeWorkflowsSrcDir = (0, import_node_path.join)(stubsDir, "claude-workflows");
|
|
4083
|
+
const claudeWorkflowsDestDir = (0, import_node_path.resolve)(rootDir, ".claude/omnify/workflows");
|
|
4084
|
+
if ((0, import_node_fs.existsSync)(claudeWorkflowsSrcDir)) {
|
|
4085
|
+
const files = copyStubs(claudeWorkflowsSrcDir, claudeWorkflowsDestDir);
|
|
4086
|
+
result.claudeWorkflows = files.length;
|
|
4087
|
+
result.files.push(...files);
|
|
4088
|
+
}
|
|
4089
|
+
const claudeAgentsSrcDir = (0, import_node_path.join)(stubsDir, "claude-agents");
|
|
4090
|
+
const claudeAgentsDestDir = (0, import_node_path.resolve)(rootDir, ".claude/omnify/agents");
|
|
4091
|
+
if ((0, import_node_fs.existsSync)(claudeAgentsSrcDir)) {
|
|
4092
|
+
const files = copyStubs(claudeAgentsSrcDir, claudeAgentsDestDir);
|
|
4093
|
+
result.claudeAgents = files.length;
|
|
4094
|
+
result.files.push(...files);
|
|
4095
|
+
}
|
|
4096
|
+
const claudeOmnifySrcDir = (0, import_node_path.join)(stubsDir, "claude-omnify");
|
|
4097
|
+
const claudeOmnifyDestDir = (0, import_node_path.resolve)(rootDir, ".claude/omnify/guides/omnify");
|
|
4098
|
+
if ((0, import_node_fs.existsSync)(claudeOmnifySrcDir)) {
|
|
4099
|
+
const files = copyStubs(claudeOmnifySrcDir, claudeOmnifyDestDir);
|
|
4100
|
+
result.claudeOmnify = files.length;
|
|
4101
|
+
result.files.push(...files);
|
|
4102
|
+
}
|
|
4103
|
+
const cursorSrcDir = (0, import_node_path.join)(stubsDir, "cursor");
|
|
4104
|
+
const cursorDestDir = (0, import_node_path.resolve)(rootDir, ".cursor/rules/omnify");
|
|
4105
|
+
if ((0, import_node_fs.existsSync)(cursorSrcDir)) {
|
|
4106
|
+
const files = copyStubs(
|
|
4107
|
+
cursorSrcDir,
|
|
4108
|
+
cursorDestDir,
|
|
4109
|
+
(content) => replacePlaceholders(content, basePath)
|
|
4110
|
+
);
|
|
4111
|
+
result.cursorRules = files.length;
|
|
4112
|
+
result.files.push(...files);
|
|
4113
|
+
}
|
|
4114
|
+
return result;
|
|
4115
|
+
}
|
|
4116
|
+
function shouldGenerateAIGuides(rootDir) {
|
|
4117
|
+
const claudeDir = (0, import_node_path.resolve)(rootDir, ".claude/omnify/guides/laravel");
|
|
4118
|
+
const cursorDir = (0, import_node_path.resolve)(rootDir, ".cursor/rules/omnify");
|
|
4119
|
+
if (!(0, import_node_fs.existsSync)(claudeDir) || !(0, import_node_fs.existsSync)(cursorDir)) {
|
|
4120
|
+
return true;
|
|
4121
|
+
}
|
|
4122
|
+
try {
|
|
4123
|
+
const claudeFiles = (0, import_node_fs.readdirSync)(claudeDir);
|
|
4124
|
+
const cursorFiles = (0, import_node_fs.readdirSync)(cursorDir);
|
|
4125
|
+
const hasLaravelRules = cursorFiles.some((f) => f.startsWith("laravel"));
|
|
4126
|
+
return claudeFiles.length === 0 || !hasLaravelRules;
|
|
4127
|
+
} catch {
|
|
4128
|
+
return true;
|
|
4129
|
+
}
|
|
4130
|
+
}
|
|
4131
|
+
|
|
3974
4132
|
// src/plugin.ts
|
|
3975
4133
|
function inferLaravelRoot(providersPath) {
|
|
3976
4134
|
const normalized = providersPath.replace(/\\/g, "/");
|
|
@@ -3986,11 +4144,11 @@ function inferLaravelRoot(providersPath) {
|
|
|
3986
4144
|
}
|
|
3987
4145
|
function getExistingMigrationTables(migrationsDir) {
|
|
3988
4146
|
const existingTables = /* @__PURE__ */ new Set();
|
|
3989
|
-
if (!(0,
|
|
4147
|
+
if (!(0, import_node_fs2.existsSync)(migrationsDir)) {
|
|
3990
4148
|
return existingTables;
|
|
3991
4149
|
}
|
|
3992
4150
|
try {
|
|
3993
|
-
const files = (0,
|
|
4151
|
+
const files = (0, import_node_fs2.readdirSync)(migrationsDir);
|
|
3994
4152
|
const createMigrationPattern = /^\d{4}_\d{2}_\d{2}_\d{6}_create_(.+)_table\.php$/;
|
|
3995
4153
|
for (const file of files) {
|
|
3996
4154
|
const match = file.match(createMigrationPattern);
|
|
@@ -4156,7 +4314,7 @@ function laravelPlugin(options) {
|
|
|
4156
4314
|
customTypes: ctx.customTypes
|
|
4157
4315
|
};
|
|
4158
4316
|
const outputs = [];
|
|
4159
|
-
const migrationsDir = (0,
|
|
4317
|
+
const migrationsDir = (0, import_node_path2.join)(ctx.cwd, resolved.migrationsPath);
|
|
4160
4318
|
const existingTables = getExistingMigrationTables(migrationsDir);
|
|
4161
4319
|
if (ctx.changes !== void 0) {
|
|
4162
4320
|
if (ctx.changes.length === 0) {
|
|
@@ -4256,20 +4414,20 @@ function laravelPlugin(options) {
|
|
|
4256
4414
|
const laravelRoot = inferLaravelRoot(resolved.providersPath);
|
|
4257
4415
|
const bootstrapProvidersRelPath = laravelRoot ? `${laravelRoot}/bootstrap/providers.php` : "bootstrap/providers.php";
|
|
4258
4416
|
const configAppRelPath = laravelRoot ? `${laravelRoot}/config/app.php` : "config/app.php";
|
|
4259
|
-
const bootstrapProvidersPath = (0,
|
|
4260
|
-
const configAppPath = (0,
|
|
4417
|
+
const bootstrapProvidersPath = (0, import_node_path2.join)(ctx.cwd, bootstrapProvidersRelPath);
|
|
4418
|
+
const configAppPath = (0, import_node_path2.join)(ctx.cwd, configAppRelPath);
|
|
4261
4419
|
let existingContent = null;
|
|
4262
4420
|
let laravelVersion;
|
|
4263
|
-
if ((0,
|
|
4421
|
+
if ((0, import_node_fs2.existsSync)(bootstrapProvidersPath)) {
|
|
4264
4422
|
laravelVersion = "laravel11+";
|
|
4265
4423
|
try {
|
|
4266
|
-
existingContent = (0,
|
|
4424
|
+
existingContent = (0, import_node_fs2.readFileSync)(bootstrapProvidersPath, "utf-8");
|
|
4267
4425
|
} catch {
|
|
4268
4426
|
existingContent = null;
|
|
4269
4427
|
}
|
|
4270
|
-
} else if ((0,
|
|
4428
|
+
} else if ((0, import_node_fs2.existsSync)(configAppPath)) {
|
|
4271
4429
|
try {
|
|
4272
|
-
const configContent = (0,
|
|
4430
|
+
const configContent = (0, import_node_fs2.readFileSync)(configAppPath, "utf-8");
|
|
4273
4431
|
if (/'providers'\s*=>\s*\[/.test(configContent)) {
|
|
4274
4432
|
laravelVersion = "laravel10-";
|
|
4275
4433
|
existingContent = configContent;
|
|
@@ -4382,6 +4540,24 @@ function laravelPlugin(options) {
|
|
|
4382
4540
|
}));
|
|
4383
4541
|
}
|
|
4384
4542
|
};
|
|
4543
|
+
const aiGuidesGenerator = {
|
|
4544
|
+
name: "laravel-ai-guides",
|
|
4545
|
+
description: "Generate AI assistant guides (Claude, Cursor) for Laravel development",
|
|
4546
|
+
generate: async (ctx) => {
|
|
4547
|
+
if (!shouldGenerateAIGuides(ctx.cwd)) {
|
|
4548
|
+
ctx.logger.debug("AI guides already exist, skipping");
|
|
4549
|
+
return [];
|
|
4550
|
+
}
|
|
4551
|
+
const result = generateAIGuides(ctx.cwd, {
|
|
4552
|
+
modelsPath: resolved.modelsPath,
|
|
4553
|
+
migrationsPath: resolved.migrationsPath,
|
|
4554
|
+
laravelBasePath: "app"
|
|
4555
|
+
});
|
|
4556
|
+
const claudeTotal = result.claudeGuides + result.claudeRules + result.claudeChecklists + result.claudeWorkflows + result.claudeAgents + result.claudeOmnify;
|
|
4557
|
+
ctx.logger.info(`Generated ${claudeTotal} Claude files, ${result.cursorRules} Cursor rules`);
|
|
4558
|
+
return [];
|
|
4559
|
+
}
|
|
4560
|
+
};
|
|
4385
4561
|
const generators = [migrationGenerator];
|
|
4386
4562
|
if (resolved.generateModels) {
|
|
4387
4563
|
generators.push(modelGenerator);
|
|
@@ -4395,6 +4571,7 @@ function laravelPlugin(options) {
|
|
|
4395
4571
|
if (resolved.generateResources) {
|
|
4396
4572
|
generators.push(resourceGenerator);
|
|
4397
4573
|
}
|
|
4574
|
+
generators.push(aiGuidesGenerator);
|
|
4398
4575
|
return {
|
|
4399
4576
|
name: "@famgia/omnify-laravel",
|
|
4400
4577
|
version: "0.0.14",
|
|
@@ -4408,6 +4585,7 @@ function laravelPlugin(options) {
|
|
|
4408
4585
|
formatForeignKey,
|
|
4409
4586
|
formatIndex,
|
|
4410
4587
|
formatMigrationFile,
|
|
4588
|
+
generateAIGuides,
|
|
4411
4589
|
generateAlterMigration,
|
|
4412
4590
|
generateDropMigrationForTable,
|
|
4413
4591
|
generateDropTableMigration,
|
|
@@ -4427,6 +4605,7 @@ function laravelPlugin(options) {
|
|
|
4427
4605
|
laravelPlugin,
|
|
4428
4606
|
propertyToColumnMethod,
|
|
4429
4607
|
schemaToBlueprint,
|
|
4608
|
+
shouldGenerateAIGuides,
|
|
4430
4609
|
toColumnName,
|
|
4431
4610
|
toTableName
|
|
4432
4611
|
});
|