Module: Command::WriteCommit

Included in:
CherryPick, Commit, Merge, Revert
Defined in:
lib/command/shared/write_commit.rb

Constant Summary collapse

CONFLICT_MESSAGE =
<<~MSG
  hint: Fix them up in the work tree, and then use 'jit add/rm <file>'
  hint: as appropriate to mark resolution and make a commit.
  fatal: Exiting because of an unresolved conflict.
MSG
MERGE_NOTES =
<<~MSG

  It looks like you may be committing a merge.
  If this is not correct, please remove the file
  \t.git/MERGE_HEAD
  and try again.
MSG
CHERRY_PICK_NOTES =
<<~MSG

  It looks like you may be committing a cherry-pick.
  If this is not correct, please remove the file
  \t.git/CHERRY_PICK_HEAD
  and try again.
MSG

Instance Method Summary collapse

Instance Method Details

#commit_message_pathObject



153
154
155
# File 'lib/command/shared/write_commit.rb', line 153

def commit_message_path
  repo.git_path.join("COMMIT_EDITMSG")
end

#compose_merge_message(notes = nil) ⇒ Object



144
145
146
147
148
149
150
151
# File 'lib/command/shared/write_commit.rb', line 144

def compose_merge_message(notes = nil)
  edit_file(commit_message_path) do |editor|
    editor.puts(pending_commit.merge_message)
    editor.note(notes) if notes
    editor.puts("")
    editor.note(Commit::COMMIT_NOTES)
  end
end

#current_authorObject



71
72
73
74
75
76
77
78
79
# File 'lib/command/shared/write_commit.rb', line 71

def current_author
  config_name  = repo.config.get(["user", "name"])
  config_email = repo.config.get(["user", "email"])

  name  = @env.fetch("GIT_AUTHOR_NAME", config_name)
  email = @env.fetch("GIT_AUTHOR_EMAIL", config_email)

  Database::Author.new(name, email, Time.now)
end

#define_write_commit_optionsObject



26
27
28
29
30
31
32
33
34
35
36
37
38
39
# File 'lib/command/shared/write_commit.rb', line 26

def define_write_commit_options
  @options[:edit] = :auto
  @parser.on("-e", "--[no-]edit") { |value| @options[:edit] = value }

  @parser.on "-m <message>", "--message=<message>" do |message|
    @options[:message] = message
    @options[:edit]    = false if @options[:edit] == :auto
  end

  @parser.on "-F <file>", "--file=<file>" do |file|
    @options[:file] = expanded_pathname(file)
    @options[:edit] = false if @options[:edit] == :auto
  end
end

#handle_conflicted_indexObject



157
158
159
160
161
162
163
164
# File 'lib/command/shared/write_commit.rb', line 157

def handle_conflicted_index
  return unless repo.index.conflict?

  message = "Committing is not possible because you have unmerged files"
  @stderr.puts "error: #{ message }."
  @stderr.puts CONFLICT_MESSAGE
  exit 128
end

#pending_commitObject



92
93
94
# File 'lib/command/shared/write_commit.rb', line 92

def pending_commit
  @pending_commit ||= repo.pending_commit
end


81
82
83
84
85
86
87
88
89
90
# File 'lib/command/shared/write_commit.rb', line 81

def print_commit(commit)
  ref  = repo.refs.current_ref
  info = ref.head? ? "detached HEAD" : ref.short_name
  oid  = repo.database.short_oid(commit.oid)

  info.concat(" (root-commit)") unless commit.parent
  info.concat(" #{ oid }")

  puts "[#{ info }] #{ commit.title_line }"
end

#read_messageObject



41
42
43
44
45
46
47
# File 'lib/command/shared/write_commit.rb', line 41

def read_message
  if @options.has_key?(:message)
    "#{ @options[:message] }\n"
  elsif @options.has_key?(:file)
    File.read(@options[:file])
  end
end

#resume_merge(type) ⇒ Object



96
97
98
99
100
101
102
103
104
# File 'lib/command/shared/write_commit.rb', line 96

def resume_merge(type)
  case type
  when :merge       then write_merge_commit
  when :cherry_pick then write_cherry_pick_commit
  when :revert      then write_revert_commit
  end

  exit 0
end

#write_cherry_pick_commitObject



116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
# File 'lib/command/shared/write_commit.rb', line 116

def write_cherry_pick_commit
  handle_conflicted_index

  parents = [repo.refs.read_head]
  message = compose_merge_message(CHERRY_PICK_NOTES)

  pick_oid = pending_commit.merge_oid(:cherry_pick)
  commit   = repo.database.load(pick_oid)

  picked = Database::Commit.new(parents, write_tree.oid,
                                commit.author, current_author,
                                message)

  repo.database.store(picked)
  repo.refs.update_head(picked.oid)
  pending_commit.clear(:cherry_pick)
end

#write_commit(parents, message) ⇒ Object



49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
# File 'lib/command/shared/write_commit.rb', line 49

def write_commit(parents, message)
  unless message
    @stderr.puts "Aborting commit due to empty commit message."
    exit 1
  end

  tree   = write_tree
  author = current_author
  commit = Database::Commit.new(parents, tree.oid, author, author, message)

  repo.database.store(commit)
  repo.refs.update_head(commit.oid)

  commit
end

#write_merge_commitObject



106
107
108
109
110
111
112
113
114
# File 'lib/command/shared/write_commit.rb', line 106

def write_merge_commit
  handle_conflicted_index

  parents = [repo.refs.read_head, pending_commit.merge_oid]
  message = compose_merge_message(MERGE_NOTES)
  write_commit(parents, message)

  pending_commit.clear(:merge)
end

#write_revert_commitObject



134
135
136
137
138
139
140
141
142
# File 'lib/command/shared/write_commit.rb', line 134

def write_revert_commit
  handle_conflicted_index

  parents = [repo.refs.read_head]
  message = compose_merge_message
  write_commit(parents, message)

  pending_commit.clear(:revert)
end

#write_treeObject



65
66
67
68
69
# File 'lib/command/shared/write_commit.rb', line 65

def write_tree
  root = Database::Tree.build(repo.index.each_entry)
  root.traverse { |tree| repo.database.store(tree) }
  root
end