reposer 1.1.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.
- checksums.yaml +7 -0
- data/.rspec +3 -0
- data/.rubocop.yml +33 -0
- data/.ruby-version +1 -0
- data/CHANGELOG.md +203 -0
- data/Gemfile +21 -0
- data/Gemfile.lock +151 -0
- data/LICENSE +21 -0
- data/README.md +489 -0
- data/READY_FOR_RELEASE.md +201 -0
- data/RELEASE_GUIDE.md +183 -0
- data/Rakefile +34 -0
- data/demo.rb +43 -0
- data/demo_ai_providers.rb +261 -0
- data/demo_interactive.rb +111 -0
- data/exe/repose +6 -0
- data/exe/reposer +6 -0
- data/lib/repose/ai/gemini_provider.rb +193 -0
- data/lib/repose/ai/ollama_provider.rb +204 -0
- data/lib/repose/ai_generator.rb +172 -0
- data/lib/repose/cli.rb +180 -0
- data/lib/repose/config.rb +47 -0
- data/lib/repose/errors.rb +17 -0
- data/lib/repose/github_client.rb +52 -0
- data/lib/repose/version.rb +5 -0
- data/lib/repose.rb +20 -0
- data/recreate_repo.rb +74 -0
- data/setup_github_repo.rb +92 -0
- metadata +186 -0
data/lib/repose/cli.rb
ADDED
|
@@ -0,0 +1,180 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require "thor"
|
|
4
|
+
require "pastel"
|
|
5
|
+
require "tty-prompt"
|
|
6
|
+
require "tty-spinner"
|
|
7
|
+
|
|
8
|
+
module Repose
|
|
9
|
+
class CLI < Thor
|
|
10
|
+
def self.exit_on_failure?
|
|
11
|
+
true
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
desc "create [NAME]", "Create a new repository with AI assistance"
|
|
15
|
+
long_desc <<~DESC
|
|
16
|
+
Create a new GitHub repository with AI-generated description, topics,
|
|
17
|
+
and README. The AI will analyze the repository name and any additional
|
|
18
|
+
context you provide to generate appropriate content.
|
|
19
|
+
|
|
20
|
+
Examples:
|
|
21
|
+
$ repose create my-awesome-project
|
|
22
|
+
$ repose create web-scraper --language ruby --framework rails
|
|
23
|
+
DESC
|
|
24
|
+
option :language, type: :string, desc: "Primary programming language"
|
|
25
|
+
option :framework, type: :string, desc: "Framework or library to use"
|
|
26
|
+
option :description, type: :string, desc: "Custom description override"
|
|
27
|
+
option :private, type: :boolean, default: false, desc: "Create private repository"
|
|
28
|
+
option :template, type: :string, desc: "Repository template to use"
|
|
29
|
+
option :topics, type: :array, desc: "Custom topics/tags"
|
|
30
|
+
option :dry_run, type: :boolean, default: false, desc: "Preview without creating"
|
|
31
|
+
def create(name = nil)
|
|
32
|
+
pastel = Pastel.new
|
|
33
|
+
prompt = TTY::Prompt.new
|
|
34
|
+
|
|
35
|
+
puts pastel.cyan("🎯 Repose - AI Repository Creator")
|
|
36
|
+
puts pastel.dim("=" * 40)
|
|
37
|
+
|
|
38
|
+
# Get repository name
|
|
39
|
+
name ||= prompt.ask("Repository name:", required: true) do |q|
|
|
40
|
+
q.validate(/\A[a-zA-Z0-9._-]+\z/, "Invalid repository name format")
|
|
41
|
+
end
|
|
42
|
+
|
|
43
|
+
# Gather context
|
|
44
|
+
context = gather_context(name, options, prompt)
|
|
45
|
+
|
|
46
|
+
# Generate AI content
|
|
47
|
+
spinner = TTY::Spinner.new("[:spinner] Generating repository content with AI...", format: :dots)
|
|
48
|
+
spinner.auto_spin
|
|
49
|
+
|
|
50
|
+
begin
|
|
51
|
+
ai_content = AIGenerator.new.generate(context)
|
|
52
|
+
spinner.success("✅")
|
|
53
|
+
rescue => e
|
|
54
|
+
spinner.error("❌")
|
|
55
|
+
puts pastel.red("Error generating AI content: #{e.message}")
|
|
56
|
+
exit 1
|
|
57
|
+
end
|
|
58
|
+
|
|
59
|
+
# Display preview
|
|
60
|
+
display_preview(ai_content, pastel)
|
|
61
|
+
|
|
62
|
+
# Confirm creation
|
|
63
|
+
unless options[:dry_run]
|
|
64
|
+
if prompt.yes?("Create repository?")
|
|
65
|
+
create_repository(name, ai_content, options, pastel)
|
|
66
|
+
else
|
|
67
|
+
puts pastel.yellow("Repository creation cancelled.")
|
|
68
|
+
end
|
|
69
|
+
end
|
|
70
|
+
end
|
|
71
|
+
|
|
72
|
+
desc "configure", "Configure Repose settings"
|
|
73
|
+
def configure
|
|
74
|
+
prompt = TTY::Prompt.new
|
|
75
|
+
config = Repose.config
|
|
76
|
+
|
|
77
|
+
puts "🔧 Configuring Repose..."
|
|
78
|
+
|
|
79
|
+
github_token = prompt.mask("GitHub Personal Access Token:")
|
|
80
|
+
config.github_token = github_token unless github_token.empty?
|
|
81
|
+
|
|
82
|
+
openai_key = prompt.mask("OpenAI API Key:")
|
|
83
|
+
config.openai_api_key = openai_key unless openai_key.empty?
|
|
84
|
+
|
|
85
|
+
default_topics = prompt.ask("Default topics (comma-separated):")
|
|
86
|
+
config.default_topics = default_topics.split(",").map(&:strip) unless default_topics.empty?
|
|
87
|
+
|
|
88
|
+
config.save!
|
|
89
|
+
puts "✅ Configuration saved!"
|
|
90
|
+
end
|
|
91
|
+
|
|
92
|
+
desc "version", "Display version information"
|
|
93
|
+
def version
|
|
94
|
+
puts "Repose v#{Repose::VERSION}"
|
|
95
|
+
end
|
|
96
|
+
|
|
97
|
+
private
|
|
98
|
+
|
|
99
|
+
def gather_context(name, options, prompt)
|
|
100
|
+
context = {
|
|
101
|
+
name: name,
|
|
102
|
+
language: options[:language],
|
|
103
|
+
framework: options[:framework],
|
|
104
|
+
description: options[:description],
|
|
105
|
+
topics: options[:topics] || []
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
# Interactive prompts for missing context
|
|
109
|
+
unless context[:language]
|
|
110
|
+
languages = %w[ruby python javascript typescript java go rust php swift kotlin]
|
|
111
|
+
context[:language] = prompt.select("Primary programming language:", languages, per_page: 10)
|
|
112
|
+
end
|
|
113
|
+
|
|
114
|
+
unless context[:framework]
|
|
115
|
+
frameworks = framework_suggestions(context[:language])
|
|
116
|
+
if frameworks.any?
|
|
117
|
+
context[:framework] = prompt.select("Framework/Library (optional):", ["None"] + frameworks)
|
|
118
|
+
context[:framework] = nil if context[:framework] == "None"
|
|
119
|
+
end
|
|
120
|
+
end
|
|
121
|
+
|
|
122
|
+
# Additional context
|
|
123
|
+
context[:purpose] = prompt.ask("What will this project do? (optional):")
|
|
124
|
+
|
|
125
|
+
context
|
|
126
|
+
end
|
|
127
|
+
|
|
128
|
+
def framework_suggestions(language)
|
|
129
|
+
frameworks = {
|
|
130
|
+
"ruby" => ["Rails", "Sinatra", "Hanami", "Roda"],
|
|
131
|
+
"javascript" => ["React", "Vue", "Express", "Next.js", "Nuxt"],
|
|
132
|
+
"typescript" => ["React", "Vue", "Express", "Next.js", "Nuxt", "Angular"],
|
|
133
|
+
"python" => ["Django", "Flask", "FastAPI", "Streamlit"],
|
|
134
|
+
"java" => ["Spring Boot", "Quarkus", "Micronaut"],
|
|
135
|
+
"go" => ["Gin", "Echo", "Fiber", "Chi"],
|
|
136
|
+
"rust" => ["Actix", "Axum", "Warp", "Rocket"],
|
|
137
|
+
"swift" => ["Vapor", "Perfect", "Kitura"]
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
frameworks[language] || []
|
|
141
|
+
end
|
|
142
|
+
|
|
143
|
+
def display_preview(content, pastel)
|
|
144
|
+
puts "\n" + pastel.cyan("📋 Generated Repository Content")
|
|
145
|
+
puts pastel.dim("-" * 40)
|
|
146
|
+
|
|
147
|
+
puts pastel.bold("Name: ") + content[:name]
|
|
148
|
+
puts pastel.bold("Description: ") + content[:description]
|
|
149
|
+
puts pastel.bold("Topics: ") + content[:topics].join(", ")
|
|
150
|
+
|
|
151
|
+
puts "\n" + pastel.bold("README Preview:")
|
|
152
|
+
puts pastel.dim(content[:readme][0..300] + "...")
|
|
153
|
+
puts
|
|
154
|
+
end
|
|
155
|
+
|
|
156
|
+
def create_repository(name, content, options, pastel)
|
|
157
|
+
spinner = TTY::Spinner.new("[:spinner] Creating GitHub repository...", format: :dots)
|
|
158
|
+
spinner.auto_spin
|
|
159
|
+
|
|
160
|
+
begin
|
|
161
|
+
github_client = GitHubClient.new
|
|
162
|
+
repo = github_client.create_repository(
|
|
163
|
+
name: name,
|
|
164
|
+
description: content[:description],
|
|
165
|
+
private: options[:private],
|
|
166
|
+
topics: content[:topics],
|
|
167
|
+
readme: content[:readme]
|
|
168
|
+
)
|
|
169
|
+
|
|
170
|
+
spinner.success("✅")
|
|
171
|
+
puts pastel.green("Repository created successfully!")
|
|
172
|
+
puts pastel.cyan("🔗 #{repo.html_url}")
|
|
173
|
+
rescue => e
|
|
174
|
+
spinner.error("❌")
|
|
175
|
+
puts pastel.red("Error creating repository: #{e.message}")
|
|
176
|
+
exit 1
|
|
177
|
+
end
|
|
178
|
+
end
|
|
179
|
+
end
|
|
180
|
+
end
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require "yaml"
|
|
4
|
+
|
|
5
|
+
module Repose
|
|
6
|
+
class Config
|
|
7
|
+
attr_accessor :github_token, :openai_api_key, :default_topics, :default_language
|
|
8
|
+
|
|
9
|
+
def initialize
|
|
10
|
+
@default_topics = []
|
|
11
|
+
load_config
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
def config_file_path
|
|
15
|
+
File.expand_path("~/.repose.yml")
|
|
16
|
+
end
|
|
17
|
+
|
|
18
|
+
def load_config
|
|
19
|
+
return unless File.exist?(config_file_path)
|
|
20
|
+
|
|
21
|
+
config = YAML.load_file(config_file_path)
|
|
22
|
+
@github_token = config["github_token"]
|
|
23
|
+
@openai_api_key = config["openai_api_key"]
|
|
24
|
+
@default_topics = config["default_topics"] || []
|
|
25
|
+
@default_language = config["default_language"]
|
|
26
|
+
rescue => e
|
|
27
|
+
warn "Warning: Could not load config file: #{e.message}"
|
|
28
|
+
end
|
|
29
|
+
|
|
30
|
+
def save!
|
|
31
|
+
config_hash = {
|
|
32
|
+
"github_token" => @github_token,
|
|
33
|
+
"openai_api_key" => @openai_api_key,
|
|
34
|
+
"default_topics" => @default_topics,
|
|
35
|
+
"default_language" => @default_language
|
|
36
|
+
}.compact
|
|
37
|
+
|
|
38
|
+
File.write(config_file_path, YAML.dump(config_hash))
|
|
39
|
+
File.chmod(0600, config_file_path) # Secure the config file
|
|
40
|
+
end
|
|
41
|
+
|
|
42
|
+
def valid?
|
|
43
|
+
!@github_token.nil? && !@github_token.empty? &&
|
|
44
|
+
!@openai_api_key.nil? && !@openai_api_key.empty?
|
|
45
|
+
end
|
|
46
|
+
end
|
|
47
|
+
end
|
|
@@ -0,0 +1,17 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
module Repose
|
|
4
|
+
module Errors
|
|
5
|
+
class Error < StandardError; end
|
|
6
|
+
class ConfigError < Error; end
|
|
7
|
+
class GitHubError < Error; end
|
|
8
|
+
class AIError < Error; end
|
|
9
|
+
class ValidationError < Error; end
|
|
10
|
+
end
|
|
11
|
+
|
|
12
|
+
# Convenience aliases for AI providers
|
|
13
|
+
ConfigurationError = Errors::ConfigError
|
|
14
|
+
APIError = Errors::AIError
|
|
15
|
+
AuthenticationError = Errors::AIError
|
|
16
|
+
RateLimitError = Errors::AIError
|
|
17
|
+
end
|
|
@@ -0,0 +1,52 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require "octokit"
|
|
4
|
+
|
|
5
|
+
module Repose
|
|
6
|
+
class GitHubClient
|
|
7
|
+
def initialize
|
|
8
|
+
@client = Octokit::Client.new(access_token: Repose.config.github_token)
|
|
9
|
+
end
|
|
10
|
+
|
|
11
|
+
def create_repository(name:, description:, private: false, topics: [], readme: nil)
|
|
12
|
+
# Create the repository
|
|
13
|
+
repo = @client.create_repository(name, {
|
|
14
|
+
description: description,
|
|
15
|
+
private: private,
|
|
16
|
+
auto_init: false # We'll create our own README
|
|
17
|
+
})
|
|
18
|
+
|
|
19
|
+
# Add topics if provided
|
|
20
|
+
if topics.any?
|
|
21
|
+
@client.replace_all_topics(repo.full_name, topics.map(&:downcase))
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
# Create README if provided
|
|
25
|
+
if readme
|
|
26
|
+
@client.create_contents(
|
|
27
|
+
repo.full_name,
|
|
28
|
+
"README.md",
|
|
29
|
+
"Initial README",
|
|
30
|
+
readme,
|
|
31
|
+
branch: repo.default_branch
|
|
32
|
+
)
|
|
33
|
+
end
|
|
34
|
+
|
|
35
|
+
repo
|
|
36
|
+
rescue Octokit::Error => e
|
|
37
|
+
raise Errors::GitHubError, "GitHub API error: #{e.message}"
|
|
38
|
+
end
|
|
39
|
+
|
|
40
|
+
def repository_exists?(name)
|
|
41
|
+
@client.repository?("#{@client.user.login}/#{name}")
|
|
42
|
+
rescue Octokit::NotFound
|
|
43
|
+
false
|
|
44
|
+
end
|
|
45
|
+
|
|
46
|
+
def user_info
|
|
47
|
+
@client.user
|
|
48
|
+
rescue Octokit::Error => e
|
|
49
|
+
raise Errors::GitHubError, "Failed to fetch user info: #{e.message}"
|
|
50
|
+
end
|
|
51
|
+
end
|
|
52
|
+
end
|
data/lib/repose.rb
ADDED
|
@@ -0,0 +1,20 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require_relative "repose/version"
|
|
4
|
+
require_relative "repose/cli"
|
|
5
|
+
require_relative "repose/github_client"
|
|
6
|
+
require_relative "repose/ai_generator"
|
|
7
|
+
require_relative "repose/config"
|
|
8
|
+
require_relative "repose/errors"
|
|
9
|
+
|
|
10
|
+
module Repose
|
|
11
|
+
class << self
|
|
12
|
+
def config
|
|
13
|
+
@config ||= Config.new
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
def configure
|
|
17
|
+
yield config if block_given?
|
|
18
|
+
end
|
|
19
|
+
end
|
|
20
|
+
end
|
data/recreate_repo.rb
ADDED
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
#!/usr/bin/env ruby
|
|
2
|
+
# frozen_string_literal: true
|
|
3
|
+
|
|
4
|
+
require 'net/http'
|
|
5
|
+
require 'json'
|
|
6
|
+
require 'uri'
|
|
7
|
+
|
|
8
|
+
def create_repo_with_personal_account
|
|
9
|
+
puts "🗑️ First, please manually delete the repository at:"
|
|
10
|
+
puts " https://github.com/svc-twm-crs/repose"
|
|
11
|
+
puts " Go to Settings > Danger Zone > Delete this repository"
|
|
12
|
+
puts ""
|
|
13
|
+
|
|
14
|
+
print "✅ Have you deleted the repository? (y/N): "
|
|
15
|
+
response = gets.chomp.downcase
|
|
16
|
+
|
|
17
|
+
unless response == 'y' || response == 'yes'
|
|
18
|
+
puts "❌ Please delete the repository first, then run this script again."
|
|
19
|
+
exit 1
|
|
20
|
+
end
|
|
21
|
+
|
|
22
|
+
puts ""
|
|
23
|
+
puts "📝 To create the repository under your personal account:"
|
|
24
|
+
puts "1. Go to: https://github.com/new"
|
|
25
|
+
puts "2. Repository name: repose"
|
|
26
|
+
puts "3. Description: AI-powered GitHub repository creation and management tool written in Ruby"
|
|
27
|
+
puts "4. Make it Public"
|
|
28
|
+
puts "5. Don't initialize with README (we have our own)"
|
|
29
|
+
puts "6. Click 'Create repository'"
|
|
30
|
+
puts ""
|
|
31
|
+
|
|
32
|
+
print "✅ Have you created the repository? (y/N): "
|
|
33
|
+
response = gets.chomp.downcase
|
|
34
|
+
|
|
35
|
+
unless response == 'y' || response == 'yes'
|
|
36
|
+
puts "❌ Please create the repository first, then run this script again."
|
|
37
|
+
exit 1
|
|
38
|
+
end
|
|
39
|
+
|
|
40
|
+
# Add the correct remote
|
|
41
|
+
puts ""
|
|
42
|
+
puts "🔗 Adding remote for wesleyscholl/repose..."
|
|
43
|
+
|
|
44
|
+
success = system("git remote add origin https://github.com/wesleyscholl/repose.git")
|
|
45
|
+
|
|
46
|
+
if success
|
|
47
|
+
puts "✅ Remote added successfully!"
|
|
48
|
+
|
|
49
|
+
puts "📤 Pushing to your repository..."
|
|
50
|
+
push_success = system("git push -u origin main")
|
|
51
|
+
|
|
52
|
+
if push_success
|
|
53
|
+
puts "🎉 Repository successfully created under your account!"
|
|
54
|
+
puts "🔗 https://github.com/wesleyscholl/repose"
|
|
55
|
+
|
|
56
|
+
puts ""
|
|
57
|
+
puts "🏷️ To add topics manually:"
|
|
58
|
+
puts "1. Go to: https://github.com/wesleyscholl/repose"
|
|
59
|
+
puts "2. Click the ⚙️ gear icon next to 'About'"
|
|
60
|
+
puts "3. Add these topics: ruby, cli, github, automation, ai, repository-management, thor, gem"
|
|
61
|
+
puts "4. Save changes"
|
|
62
|
+
|
|
63
|
+
else
|
|
64
|
+
puts "❌ Failed to push to repository"
|
|
65
|
+
end
|
|
66
|
+
else
|
|
67
|
+
puts "❌ Failed to add remote"
|
|
68
|
+
end
|
|
69
|
+
end
|
|
70
|
+
|
|
71
|
+
puts "🎯 Repose - Repository Recreation Script"
|
|
72
|
+
puts "=" * 50
|
|
73
|
+
|
|
74
|
+
create_repo_with_personal_account
|
|
@@ -0,0 +1,92 @@
|
|
|
1
|
+
#!/usr/bin/env ruby
|
|
2
|
+
# frozen_string_literal: true
|
|
3
|
+
|
|
4
|
+
# Simple script to create the GitHub repository for repose
|
|
5
|
+
# This demonstrates the kind of automation that repose will provide
|
|
6
|
+
|
|
7
|
+
require 'net/http'
|
|
8
|
+
require 'json'
|
|
9
|
+
require 'uri'
|
|
10
|
+
|
|
11
|
+
def create_github_repo
|
|
12
|
+
puts "🚀 Creating GitHub repository for Repose..."
|
|
13
|
+
|
|
14
|
+
# Check if gh CLI is available
|
|
15
|
+
if system('which gh > /dev/null 2>&1')
|
|
16
|
+
puts "✅ Found GitHub CLI, creating repository..."
|
|
17
|
+
|
|
18
|
+
repo_data = {
|
|
19
|
+
name: "repose",
|
|
20
|
+
description: "AI-powered GitHub repository creation and management tool written in Ruby",
|
|
21
|
+
topics: ["ruby", "cli", "github", "automation", "ai", "repository-management", "thor", "gem"],
|
|
22
|
+
private: false
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
# Create repository using GitHub CLI
|
|
26
|
+
cmd = [
|
|
27
|
+
"gh", "repo", "create", repo_data[:name],
|
|
28
|
+
"--description", repo_data[:description],
|
|
29
|
+
"--public",
|
|
30
|
+
"--source", ".",
|
|
31
|
+
"--remote", "origin",
|
|
32
|
+
"--push"
|
|
33
|
+
]
|
|
34
|
+
|
|
35
|
+
success = system(*cmd)
|
|
36
|
+
|
|
37
|
+
if success
|
|
38
|
+
puts "✅ Repository created successfully!"
|
|
39
|
+
puts "🔗 Repository URL: https://github.com/wesleyscholl/repose"
|
|
40
|
+
|
|
41
|
+
# Add topics using GitHub API
|
|
42
|
+
puts "🏷️ Adding topics..."
|
|
43
|
+
topic_cmd = [
|
|
44
|
+
"gh", "api", "-X", "PUT",
|
|
45
|
+
"/repos/wesleyscholl/repose/topics",
|
|
46
|
+
"-f", "names=#{repo_data[:topics].join(',')}"
|
|
47
|
+
]
|
|
48
|
+
|
|
49
|
+
if system(*topic_cmd)
|
|
50
|
+
puts "✅ Topics added successfully!"
|
|
51
|
+
else
|
|
52
|
+
puts "⚠️ Topics may not have been added, but repository was created"
|
|
53
|
+
end
|
|
54
|
+
|
|
55
|
+
puts "\n🎉 Next steps:"
|
|
56
|
+
puts "1. Visit: https://github.com/wesleyscholl/repose"
|
|
57
|
+
puts "2. Set up GitHub Actions for CI/CD"
|
|
58
|
+
puts "3. Configure RubyGems publishing"
|
|
59
|
+
puts "4. Add OpenAI integration when ready"
|
|
60
|
+
|
|
61
|
+
else
|
|
62
|
+
puts "❌ Failed to create repository"
|
|
63
|
+
exit 1
|
|
64
|
+
end
|
|
65
|
+
else
|
|
66
|
+
puts "❌ GitHub CLI not found. Please install it first:"
|
|
67
|
+
puts " brew install gh"
|
|
68
|
+
puts " gh auth login"
|
|
69
|
+
exit 1
|
|
70
|
+
end
|
|
71
|
+
end
|
|
72
|
+
|
|
73
|
+
def main
|
|
74
|
+
puts "🎯 Repose Repository Setup"
|
|
75
|
+
puts "=" * 40
|
|
76
|
+
|
|
77
|
+
# Check if we're in a git repository
|
|
78
|
+
unless Dir.exist?('.git')
|
|
79
|
+
puts "❌ Not in a git repository. Please run 'git init' first."
|
|
80
|
+
exit 1
|
|
81
|
+
end
|
|
82
|
+
|
|
83
|
+
# Check if there are commits
|
|
84
|
+
if `git rev-list --count HEAD 2>/dev/null`.strip == "0"
|
|
85
|
+
puts "❌ No commits found. Please make an initial commit first."
|
|
86
|
+
exit 1
|
|
87
|
+
end
|
|
88
|
+
|
|
89
|
+
create_github_repo
|
|
90
|
+
end
|
|
91
|
+
|
|
92
|
+
main if __FILE__ == $PROGRAM_NAME
|
metadata
ADDED
|
@@ -0,0 +1,186 @@
|
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
|
2
|
+
name: reposer
|
|
3
|
+
version: !ruby/object:Gem::Version
|
|
4
|
+
version: 1.1.0
|
|
5
|
+
platform: ruby
|
|
6
|
+
authors:
|
|
7
|
+
- Wesley Scholl
|
|
8
|
+
bindir: exe
|
|
9
|
+
cert_chain: []
|
|
10
|
+
date: 1980-01-02 00:00:00.000000000 Z
|
|
11
|
+
dependencies:
|
|
12
|
+
- !ruby/object:Gem::Dependency
|
|
13
|
+
name: thor
|
|
14
|
+
requirement: !ruby/object:Gem::Requirement
|
|
15
|
+
requirements:
|
|
16
|
+
- - "~>"
|
|
17
|
+
- !ruby/object:Gem::Version
|
|
18
|
+
version: '1.0'
|
|
19
|
+
type: :runtime
|
|
20
|
+
prerelease: false
|
|
21
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
22
|
+
requirements:
|
|
23
|
+
- - "~>"
|
|
24
|
+
- !ruby/object:Gem::Version
|
|
25
|
+
version: '1.0'
|
|
26
|
+
- !ruby/object:Gem::Dependency
|
|
27
|
+
name: octokit
|
|
28
|
+
requirement: !ruby/object:Gem::Requirement
|
|
29
|
+
requirements:
|
|
30
|
+
- - "~>"
|
|
31
|
+
- !ruby/object:Gem::Version
|
|
32
|
+
version: '6.0'
|
|
33
|
+
type: :runtime
|
|
34
|
+
prerelease: false
|
|
35
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
36
|
+
requirements:
|
|
37
|
+
- - "~>"
|
|
38
|
+
- !ruby/object:Gem::Version
|
|
39
|
+
version: '6.0'
|
|
40
|
+
- !ruby/object:Gem::Dependency
|
|
41
|
+
name: faraday
|
|
42
|
+
requirement: !ruby/object:Gem::Requirement
|
|
43
|
+
requirements:
|
|
44
|
+
- - "~>"
|
|
45
|
+
- !ruby/object:Gem::Version
|
|
46
|
+
version: '2.0'
|
|
47
|
+
type: :runtime
|
|
48
|
+
prerelease: false
|
|
49
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
50
|
+
requirements:
|
|
51
|
+
- - "~>"
|
|
52
|
+
- !ruby/object:Gem::Version
|
|
53
|
+
version: '2.0'
|
|
54
|
+
- !ruby/object:Gem::Dependency
|
|
55
|
+
name: pastel
|
|
56
|
+
requirement: !ruby/object:Gem::Requirement
|
|
57
|
+
requirements:
|
|
58
|
+
- - "~>"
|
|
59
|
+
- !ruby/object:Gem::Version
|
|
60
|
+
version: '0.8'
|
|
61
|
+
type: :runtime
|
|
62
|
+
prerelease: false
|
|
63
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
64
|
+
requirements:
|
|
65
|
+
- - "~>"
|
|
66
|
+
- !ruby/object:Gem::Version
|
|
67
|
+
version: '0.8'
|
|
68
|
+
- !ruby/object:Gem::Dependency
|
|
69
|
+
name: tty-prompt
|
|
70
|
+
requirement: !ruby/object:Gem::Requirement
|
|
71
|
+
requirements:
|
|
72
|
+
- - "~>"
|
|
73
|
+
- !ruby/object:Gem::Version
|
|
74
|
+
version: '0.23'
|
|
75
|
+
type: :runtime
|
|
76
|
+
prerelease: false
|
|
77
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
78
|
+
requirements:
|
|
79
|
+
- - "~>"
|
|
80
|
+
- !ruby/object:Gem::Version
|
|
81
|
+
version: '0.23'
|
|
82
|
+
- !ruby/object:Gem::Dependency
|
|
83
|
+
name: tty-spinner
|
|
84
|
+
requirement: !ruby/object:Gem::Requirement
|
|
85
|
+
requirements:
|
|
86
|
+
- - "~>"
|
|
87
|
+
- !ruby/object:Gem::Version
|
|
88
|
+
version: '0.9'
|
|
89
|
+
type: :runtime
|
|
90
|
+
prerelease: false
|
|
91
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
92
|
+
requirements:
|
|
93
|
+
- - "~>"
|
|
94
|
+
- !ruby/object:Gem::Version
|
|
95
|
+
version: '0.9'
|
|
96
|
+
- !ruby/object:Gem::Dependency
|
|
97
|
+
name: yaml
|
|
98
|
+
requirement: !ruby/object:Gem::Requirement
|
|
99
|
+
requirements:
|
|
100
|
+
- - "~>"
|
|
101
|
+
- !ruby/object:Gem::Version
|
|
102
|
+
version: '0.3'
|
|
103
|
+
type: :runtime
|
|
104
|
+
prerelease: false
|
|
105
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
106
|
+
requirements:
|
|
107
|
+
- - "~>"
|
|
108
|
+
- !ruby/object:Gem::Version
|
|
109
|
+
version: '0.3'
|
|
110
|
+
- !ruby/object:Gem::Dependency
|
|
111
|
+
name: ostruct
|
|
112
|
+
requirement: !ruby/object:Gem::Requirement
|
|
113
|
+
requirements:
|
|
114
|
+
- - "~>"
|
|
115
|
+
- !ruby/object:Gem::Version
|
|
116
|
+
version: '0.6'
|
|
117
|
+
type: :runtime
|
|
118
|
+
prerelease: false
|
|
119
|
+
version_requirements: !ruby/object:Gem::Requirement
|
|
120
|
+
requirements:
|
|
121
|
+
- - "~>"
|
|
122
|
+
- !ruby/object:Gem::Version
|
|
123
|
+
version: '0.6'
|
|
124
|
+
description: Reposer is an intelligent tool that uses AI to create GitHub repositories
|
|
125
|
+
with smart descriptions, topics, READMEs, and project structure
|
|
126
|
+
email:
|
|
127
|
+
- wesleyscholl@gmail.com
|
|
128
|
+
executables:
|
|
129
|
+
- reposer
|
|
130
|
+
extensions: []
|
|
131
|
+
extra_rdoc_files: []
|
|
132
|
+
files:
|
|
133
|
+
- ".rspec"
|
|
134
|
+
- ".rubocop.yml"
|
|
135
|
+
- ".ruby-version"
|
|
136
|
+
- CHANGELOG.md
|
|
137
|
+
- Gemfile
|
|
138
|
+
- Gemfile.lock
|
|
139
|
+
- LICENSE
|
|
140
|
+
- README.md
|
|
141
|
+
- READY_FOR_RELEASE.md
|
|
142
|
+
- RELEASE_GUIDE.md
|
|
143
|
+
- Rakefile
|
|
144
|
+
- demo.rb
|
|
145
|
+
- demo_ai_providers.rb
|
|
146
|
+
- demo_interactive.rb
|
|
147
|
+
- exe/repose
|
|
148
|
+
- exe/reposer
|
|
149
|
+
- lib/repose.rb
|
|
150
|
+
- lib/repose/ai/gemini_provider.rb
|
|
151
|
+
- lib/repose/ai/ollama_provider.rb
|
|
152
|
+
- lib/repose/ai_generator.rb
|
|
153
|
+
- lib/repose/cli.rb
|
|
154
|
+
- lib/repose/config.rb
|
|
155
|
+
- lib/repose/errors.rb
|
|
156
|
+
- lib/repose/github_client.rb
|
|
157
|
+
- lib/repose/version.rb
|
|
158
|
+
- recreate_repo.rb
|
|
159
|
+
- setup_github_repo.rb
|
|
160
|
+
homepage: https://github.com/wesleyscholl/repose
|
|
161
|
+
licenses:
|
|
162
|
+
- MIT
|
|
163
|
+
metadata:
|
|
164
|
+
allowed_push_host: https://rubygems.org
|
|
165
|
+
homepage_uri: https://github.com/wesleyscholl/repose
|
|
166
|
+
source_code_uri: https://github.com/wesleyscholl/repose
|
|
167
|
+
changelog_uri: https://github.com/wesleyscholl/repose/blob/main/CHANGELOG.md
|
|
168
|
+
rubygems_mfa_required: 'true'
|
|
169
|
+
rdoc_options: []
|
|
170
|
+
require_paths:
|
|
171
|
+
- lib
|
|
172
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
|
173
|
+
requirements:
|
|
174
|
+
- - ">="
|
|
175
|
+
- !ruby/object:Gem::Version
|
|
176
|
+
version: 3.0.0
|
|
177
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
|
178
|
+
requirements:
|
|
179
|
+
- - ">="
|
|
180
|
+
- !ruby/object:Gem::Version
|
|
181
|
+
version: '0'
|
|
182
|
+
requirements: []
|
|
183
|
+
rubygems_version: 3.7.2
|
|
184
|
+
specification_version: 4
|
|
185
|
+
summary: AI-powered GitHub repository creation and management
|
|
186
|
+
test_files: []
|