class Git::EscapedPath

Represents an escaped Git path string

Git commands that output paths (e.g. ls-files, diff), will escape usual characters in the path with backslashes in the same way C escapes control characters (e.g. t for TAB, n for LF, \ for backslash) or bytes with values larger than 0x80 (e.g. octal 302265 for “micro” in UTF-8).

@example

Git::GitPath.new('\302\265').unescape # => "µ"

Constants

UNESCAPES

Attributes

path[R]

Public Class Methods

new(path) click to toggle source
# File lib/git/escaped_path.rb, line 31
def initialize(path)
  @path = path
end

Public Instance Methods

unescape() click to toggle source

Convert an escaped path to an unescaped path

# File lib/git/escaped_path.rb, line 36
def unescape
  bytes = escaped_path_to_bytes(path)
  str = bytes.pack('C*')
  str.force_encoding(Encoding::UTF_8)
end

Private Instance Methods

escaped_path_to_bytes(path) click to toggle source
# File lib/git/escaped_path.rb, line 66
def escaped_path_to_bytes(path)
  index = 0
  [].tap do |bytes|
    while index < path.length
      byte, chars_used = next_byte(path, index)
      bytes << byte
      index += chars_used
    end
  end
end
extract_escape(path, index) click to toggle source
# File lib/git/escaped_path.rb, line 48
def extract_escape(path, index)
  [UNESCAPES[path[index + 1]], 2]
end
extract_octal(path, index) click to toggle source
# File lib/git/escaped_path.rb, line 44
def extract_octal(path, index)
  [path[index + 1..index + 3].to_i(8), 4]
end
extract_single_char(path, index) click to toggle source
# File lib/git/escaped_path.rb, line 52
def extract_single_char(path, index)
  [path[index].ord, 1]
end
next_byte(path, index) click to toggle source
# File lib/git/escaped_path.rb, line 56
def next_byte(path, index)
  if path[index] == '\\' && path[index + 1] >= '0' && path[index + 1] <= '7'
    extract_octal(path, index)
  elsif path[index] == '\\' && UNESCAPES.include?(path[index + 1])
    extract_escape(path, index)
  else
    extract_single_char(path, index)
  end
end