gitXplorer 1.0.0

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,48 @@
1
+ class GitXplorer::GitObject::File < GitXplorer::GitObject
2
+ def children
3
+ if (@kids.nil?)
4
+ # Initialize
5
+ @kids = Array.new
6
+
7
+ # Create git command
8
+ cmd = [
9
+ "git log --date=format-local:\"%F_%I:%M:%S_%P\"",
10
+ "--diff-filter=AC",
11
+ "--full-history",
12
+ "--pretty=tformat:\"{{%H}}{{%s}}{{%cd}}{{%an}}\"",
13
+ "--",
14
+ absolute_path
15
+ ].join(" ")
16
+
17
+ # Loop thru results creating a revision object for each
18
+ %x(#{cmd}).split("\n").each do |line|
19
+ line.match(/{{(.+)}}{{(.+)}}{{(.+)}}{{(.+)}}/) do |m|
20
+ @kids.push(
21
+ GitXplorer::GitObject::Revision.new(
22
+ m[1],
23
+ self,
24
+ m[2],
25
+ m[3],
26
+ m[4]
27
+ )
28
+ )
29
+ end
30
+ end
31
+ end
32
+
33
+ return @kids
34
+ end
35
+
36
+ def desc
37
+ return "#{newest.name} #{newest.date}" if (newest)
38
+ return nil
39
+ end
40
+
41
+ def initialize(name, parent)
42
+ super(name, parent)
43
+ end
44
+
45
+ def newest
46
+ return children[0]
47
+ end
48
+ end
@@ -0,0 +1,21 @@
1
+ class GitXplorer::GitObject::Revision < GitXplorer::GitObject
2
+ attr_reader :date
3
+ attr_reader :summary
4
+ attr_reader :user
5
+
6
+ def desc
7
+ return "#{@date} #{@user} #{@summary}"
8
+ end
9
+
10
+ def initialize(revision, parent, summary, date, user)
11
+ super(revision, parent)
12
+ @date = date
13
+ @summary = summary
14
+ @user = user
15
+ end
16
+
17
+ def tab_complete(color = false)
18
+ color ||= false
19
+ return {@name => @date}
20
+ end
21
+ end
@@ -0,0 +1,112 @@
1
+ class GitXplorer::GitObject
2
+ attr_reader :name
3
+ attr_reader :parent
4
+
5
+ def absolute_path
6
+ return "" if (@parent.nil?)
7
+ return [@parent.absolute_path, @name].join
8
+ end
9
+
10
+ def children
11
+ @kids ||= Array.new
12
+ return @kids
13
+ end
14
+
15
+ def desc
16
+ return ""
17
+ end
18
+
19
+ def exist?(path)
20
+ return !get(path).nil?
21
+ end
22
+
23
+ def get(path)
24
+ # Return self if path is nil or empty
25
+ return self if (path.nil? || path.empty?)
26
+
27
+ # Split path on /
28
+ child, recurse, grandchild = path.partition("/")
29
+ child, _, grandchild = path.partition(":") if (recurse.empty?)
30
+
31
+ case child
32
+ when "."
33
+ # Same directory
34
+ return self.get(grandchild)
35
+ when ".."
36
+ # Check parent if it exists
37
+ return @parent.get(grandchild) if (@parent)
38
+
39
+ # Otherwise we reached top-level so just keep going
40
+ return self.get(grandchild)
41
+ end
42
+
43
+ # Check child if it exists
44
+ if (has_child?(child))
45
+ kids = children.select do |kid|
46
+ kid.name == child
47
+ end
48
+ return kids[0].get(grandchild) if (!kids.empty?)
49
+ end
50
+
51
+ # Not found
52
+ return nil
53
+ end
54
+
55
+ def get_completions(path)
56
+ # Return all children if path is nil or empty
57
+ return children if (path.nil? || path.empty?)
58
+
59
+ # Split path on / or :
60
+ child, recurse, grandchild = path.partition("/")
61
+ if (recurse.empty?)
62
+ child, recurse, grandchild = path.partition(":")
63
+ end
64
+
65
+ case child
66
+ when "."
67
+ # Same directory
68
+ return get_completions(grandchild)
69
+ when ".."
70
+ # Check parent if it exists
71
+ return @parent.get_completions(grandchild) if (@parent)
72
+
73
+ # Otherwise we reached top-level so just keep going
74
+ return get_completions(grandchild)
75
+ end
76
+
77
+ # Check child if it exists
78
+ if (!recurse.empty? && has_child?(child))
79
+ return get(child).get_completions(grandchild)
80
+ end
81
+
82
+ # Return any children that may match
83
+ return children.select do |kid|
84
+ kid.name.downcase.start_with?(child.downcase)
85
+ end
86
+ end
87
+
88
+ def has_child?(name)
89
+ return children.any? do |child|
90
+ child.name == name
91
+ end
92
+ end
93
+
94
+ def initialize(name, parent)
95
+ @kids = nil
96
+ @name = name
97
+ @parent = parent
98
+ end
99
+
100
+ def tab_complete(color = false)
101
+ color ||= false
102
+ return {@name => desc}
103
+ end
104
+
105
+ def to_s
106
+ return @name
107
+ end
108
+ end
109
+
110
+ require "git_xplorer/git_object/directory"
111
+ require "git_xplorer/git_object/file"
112
+ require "git_xplorer/git_object/revision"
@@ -0,0 +1,40 @@
1
+ require "djinni"
2
+
3
+ class CatWish < Djinni::Wish
4
+ def aliases
5
+ return ["cat"]
6
+ end
7
+
8
+ def description
9
+ return "Display file contents"
10
+ end
11
+
12
+ def execute(args, djinni_env = Hash.new)
13
+ gitx = djinni_env["gitXplorer"]
14
+
15
+ begin
16
+ gitx.show(args)
17
+ rescue GitXplorer::Error => e
18
+ puts e.message
19
+ end
20
+ end
21
+
22
+ def tab_complete(input, djinni_env = Hash.new)
23
+ gitx = djinni_env["gitXplorer"]
24
+
25
+ _, found, partial = input.rpartition(":")
26
+ _, _, partial = input.rpartition("/") if (found.empty?)
27
+
28
+ completions = Hash.new
29
+ gitx.get_completions(input).each do |child|
30
+ completions.merge!(child.tab_complete)
31
+ end
32
+
33
+ return [completions, partial, ""]
34
+ end
35
+
36
+ def usage
37
+ puts "#{aliases.join(", ")} <file>"
38
+ puts " #{description}."
39
+ end
40
+ end
@@ -0,0 +1,44 @@
1
+ require "djinni"
2
+ require "hilighter"
3
+
4
+ class ChangeDirectoryWish < Djinni::Wish
5
+ def aliases
6
+ return ["cd"]
7
+ end
8
+
9
+ def description
10
+ return "Change to new directory"
11
+ end
12
+
13
+ def execute(args, djinni_env = Hash.new)
14
+ gitx = djinni_env["gitXplorer"]
15
+ begin
16
+ gitx.cd(args)
17
+ prompt = "#{gitx.pwd_short}$ ".light_white
18
+ djinni_env["djinni_prompt"] = prompt
19
+ rescue GitXplorer::Error => e
20
+ puts e.message
21
+ end
22
+ end
23
+
24
+ def tab_complete(input, djinni_env = Hash.new)
25
+ gitx = djinni_env["gitXplorer"]
26
+
27
+ _, _, partial = input.rpartition("/")
28
+ partial = "" if (input.end_with?("/"))
29
+
30
+ completions = Hash.new
31
+ gitx.get_completions(input).select do |child|
32
+ child.is_a?(GitXplorer::GitObject::Directory)
33
+ end.each do |child|
34
+ completions.merge!(child.tab_complete)
35
+ end
36
+
37
+ return [completions, partial, ""]
38
+ end
39
+
40
+ def usage
41
+ puts "#{aliases.join(", ")} [directory]"
42
+ puts " #{description}."
43
+ end
44
+ end
@@ -0,0 +1,28 @@
1
+ require "djinni"
2
+
3
+ class FindWish < Djinni::Wish
4
+ def aliases
5
+ return ["find"]
6
+ end
7
+
8
+ def description
9
+ return "Similar to \"find . -iregex PATTERN\""
10
+ end
11
+
12
+ def execute(args, djinni_env = Hash.new)
13
+ gitx = djinni_env["gitXplorer"]
14
+ args.gsub!(/^(["'])(.*)\1$/, "\\2")
15
+ dir = gitx.pwd.gsub(%r{^[^/]+(/|$)}, "")
16
+
17
+ begin
18
+ puts gitx.get_filenames(dir, args)
19
+ rescue GitXplorer::Error => e
20
+ puts e.message
21
+ end
22
+ end
23
+
24
+ def usage
25
+ puts "#{aliases.join(", ")} [PATTERN]"
26
+ puts " #{description}."
27
+ end
28
+ end
@@ -0,0 +1,30 @@
1
+ require "djinni"
2
+
3
+ class GitWish < Djinni::Wish
4
+ def aliases
5
+ return ["git"]
6
+ end
7
+
8
+ def description
9
+ return "Run any git command"
10
+ end
11
+
12
+ def execute(args, djinni_env = Hash.new)
13
+ gitx = djinni_env["gitXplorer"]
14
+ begin
15
+ case args
16
+ when /^\s*(diff|ls-files|rev-parse|show|status).*/
17
+ puts gitx.git(args, false)
18
+ else
19
+ puts gitx.git(args)
20
+ end
21
+ rescue GitXplorer::Error => e
22
+ puts e.message
23
+ end
24
+ end
25
+
26
+ def usage
27
+ puts "#{aliases.join(", ")}"
28
+ puts " #{description}."
29
+ end
30
+ end
@@ -0,0 +1,45 @@
1
+ require "djinni"
2
+
3
+ class GrepWish < Djinni::Wish
4
+ def aliases
5
+ return ["grep"]
6
+ end
7
+
8
+ def description
9
+ return "Similar to \"git grep -HIinP PATTERN\""
10
+ end
11
+
12
+ def execute(args, djinni_env = Hash.new)
13
+ gitx = djinni_env["gitXplorer"]
14
+ args.gsub!(/^(["'])(.*)\1$/, "\\2")
15
+ dir = gitx.pwd.gsub(%r{^[^/]+(/|$)}, "")
16
+
17
+ if (args.empty?)
18
+ usage
19
+ return
20
+ end
21
+
22
+ begin
23
+ gitx.search(dir, args).each do |line|
24
+ m = line.match(/^([^:]+):([^:]+):(\d+):(.*)$/)
25
+ if (m && (m.length == 5))
26
+ puts [
27
+ m[1].green,
28
+ m[2].cyan,
29
+ m[3].white,
30
+ m[4].gsub(/(#{args})/i, "\\1".black.on_white)
31
+ ].join(":")
32
+ else
33
+ puts line
34
+ end
35
+ end
36
+ rescue GitXplorer::Error => e
37
+ puts e.message
38
+ end
39
+ end
40
+
41
+ def usage
42
+ puts "#{aliases.join(", ")} <PATTERN>"
43
+ puts " #{description}."
44
+ end
45
+ end
@@ -0,0 +1,93 @@
1
+ require "djinni"
2
+
3
+ class ListDirectoryWish < Djinni::Wish
4
+ def aliases
5
+ return ["ls", "ll"]
6
+ end
7
+
8
+ def description
9
+ return "List directory contents or file revisions"
10
+ end
11
+
12
+ def execute(args, djinni_env = Hash.new)
13
+ gitx = djinni_env["gitXplorer"]
14
+
15
+ long = false
16
+ case djinni_env["djinni_input"]
17
+ when "ll"
18
+ long = true
19
+ end
20
+ if (args.match(/(^| )(-l|--long)( |$)/))
21
+ args.gsub!(/(^| )(-l|--long)( |$)/, "")
22
+ long = true
23
+ end
24
+
25
+ begin
26
+ children = gitx.ls(args)
27
+ if (long)
28
+ long(children)
29
+ else
30
+ children.each do |child|
31
+ puts child
32
+ end
33
+ end
34
+ rescue GitXplorer::Error => e
35
+ puts e.message
36
+ end
37
+ end
38
+
39
+ def initialize
40
+ @space = 4
41
+ end
42
+
43
+ def long(children)
44
+ max = children.max_by do |child|
45
+ child.to_s.length
46
+ end.to_s.length
47
+ nlfill = " " * (max + @space)
48
+ width = %x(tput cols).to_i - (max + @space) - 2
49
+
50
+ children.each do |child|
51
+ name = child.to_s
52
+ desc = child.desc
53
+ fill = " " * (max + @space - name.length)
54
+ fill = "" if ((max + @space - name.length) <= 0)
55
+ lines = Array.new
56
+ if (desc)
57
+ lines = desc.scan(/\S.{0,#{width}}\S(?=\s|$)|\S+/)
58
+ end
59
+ if (lines.empty?)
60
+ puts name
61
+ else
62
+ start = lines.delete_at(0)
63
+ puts "#{name}#{fill}#{start}"
64
+ lines.each do |line|
65
+ puts "#{nlfill}#{line}"
66
+ end
67
+ end
68
+ end
69
+ end
70
+ private :long
71
+
72
+ def tab_complete(input, djinni_env = Hash.new)
73
+ gitx = djinni_env["gitXplorer"]
74
+
75
+ _, found, partial = input.rpartition(":")
76
+ _, _, partial = input.rpartition("/") if (found.empty?)
77
+
78
+ completions = Hash.new
79
+ gitx.get_completions(input).each do |child|
80
+ completions.merge!(child.tab_complete)
81
+ end
82
+
83
+ return [completions, partial, ""]
84
+ end
85
+
86
+ def usage
87
+ puts "#{aliases.join(", ")} [OPTIONS] [directory/file]"
88
+ puts " #{description}."
89
+ puts
90
+ puts "OPTIONS"
91
+ puts " -l, --long Show more info for files"
92
+ end
93
+ end
@@ -0,0 +1,24 @@
1
+ require "djinni"
2
+
3
+ class PwdWish < Djinni::Wish
4
+ def aliases
5
+ return ["pwd"]
6
+ end
7
+
8
+ def description
9
+ return "Show path of current path"
10
+ end
11
+
12
+ def execute(args, djinni_env = Hash.new)
13
+ if (!args.empty?)
14
+ usage
15
+ else
16
+ puts djinni_env["gitXplorer"].pwd
17
+ end
18
+ end
19
+
20
+ def usage
21
+ puts aliases.join(", ")
22
+ puts " #{description}."
23
+ end
24
+ end
@@ -0,0 +1,46 @@
1
+ require "djinni"
2
+
3
+ class ViWish < Djinni::Wish
4
+ def aliases
5
+ return ["vi", "view", "vim"]
6
+ end
7
+
8
+ def description
9
+ return "Open the file in vim"
10
+ end
11
+
12
+ def execute(args, djinni_env = Hash.new)
13
+ gitx = djinni_env["gitXplorer"]
14
+
15
+ readonly = false
16
+ case djinni_env["djinni_input"]
17
+ when "view"
18
+ readonly = true
19
+ end
20
+
21
+ begin
22
+ gitx.vim(args, readonly)
23
+ rescue GitXplorer::Error => e
24
+ puts e.message
25
+ end
26
+ end
27
+
28
+ def tab_complete(input, djinni_env = Hash.new)
29
+ gitx = djinni_env["gitXplorer"]
30
+
31
+ _, found, partial = input.rpartition(":")
32
+ _, _, partial = input.rpartition("/") if (found.empty?)
33
+
34
+ completions = Hash.new
35
+ gitx.get_completions(input).each do |child|
36
+ completions.merge!(child.tab_complete)
37
+ end
38
+
39
+ return [completions, partial, ""]
40
+ end
41
+
42
+ def usage
43
+ puts "#{aliases.join(", ")} <file>"
44
+ puts " #{description}."
45
+ end
46
+ end