Class: Isort::ImportStatement

Inherits:
Object
  • Object
show all
Defined in:
lib/isort/import_statement.rb

Overview

Represents a single import statement with all its metadata This includes the raw line, type, sort key, and associated comments

Constant Summary collapse

IMPORT_TYPES =
%i[require require_relative include extend autoload using].freeze
TYPE_ORDER =
{
  require: 0,
  require_relative: 1,
  include: 2,
  extend: 3,
  autoload: 4,
  using: 5
}.freeze
SKIP_PATTERN =
/#\s*isort:\s*skip\b/i.freeze

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(raw_line:, type:, leading_comments: [], indentation: "") ⇒ ImportStatement

Returns a new instance of ImportStatement.



24
25
26
27
28
29
30
31
32
# File 'lib/isort/import_statement.rb', line 24

def initialize(raw_line:, type:, leading_comments: [], indentation: "")
  @raw_line = raw_line
  @type = type
  @leading_comments = leading_comments
  @indentation = indentation
  @sort_key = extract_sort_key
  @skip_sorting = has_skip_directive?
  @section = Section.classify(self)
end

Instance Attribute Details

#indentationObject (readonly)

Returns the value of attribute indentation.



21
22
23
# File 'lib/isort/import_statement.rb', line 21

def indentation
  @indentation
end

#leading_commentsObject (readonly)

Returns the value of attribute leading_comments.



21
22
23
# File 'lib/isort/import_statement.rb', line 21

def leading_comments
  @leading_comments
end

#raw_lineObject (readonly)

Returns the value of attribute raw_line.



21
22
23
# File 'lib/isort/import_statement.rb', line 21

def raw_line
  @raw_line
end

#sectionObject (readonly)

Returns the value of attribute section.



22
23
24
# File 'lib/isort/import_statement.rb', line 22

def section
  @section
end

#skip_sortingObject (readonly) Also known as: skip_sorting?

Returns the value of attribute skip_sorting.



22
23
24
# File 'lib/isort/import_statement.rb', line 22

def skip_sorting
  @skip_sorting
end

#sort_keyObject (readonly)

Returns the value of attribute sort_key.



21
22
23
# File 'lib/isort/import_statement.rb', line 21

def sort_key
  @sort_key
end

#typeObject (readonly)

Returns the value of attribute type.



21
22
23
# File 'lib/isort/import_statement.rb', line 21

def type
  @type
end

Instance Method Details

#<=>(other) ⇒ Object

Compare for sorting - first by section, then by type order, then alphabetically



90
91
92
93
94
95
96
97
98
99
100
101
# File 'lib/isort/import_statement.rb', line 90

def <=>(other)
  # First compare by section (stdlib, thirdparty, firstparty, localfolder)
  section_comparison = Section.order(@section) <=> Section.order(other.section)
  return section_comparison unless section_comparison.zero?

  # Then by type within section
  type_comparison = TYPE_ORDER[@type] <=> TYPE_ORDER[other.type]
  return type_comparison unless type_comparison.zero?

  # Finally alphabetically
  @sort_key <=> other.sort_key
end

#has_skip_directive?Boolean

Check if this import has an isort:skip directive

Returns:

  • (Boolean)


35
36
37
# File 'lib/isort/import_statement.rb', line 35

def has_skip_directive?
  @raw_line.match?(SKIP_PATTERN)
end

#normalized_keyObject

For deduplication - normalized import path/module



57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
# File 'lib/isort/import_statement.rb', line 57

def normalized_key
  @normalized_key ||= begin
    stripped = @raw_line.strip
    # Extract the actual import value for comparison
    case @type
    when :require, :require_relative
      # Extract path from require 'path' or require "path"
      if (match = stripped.match(/^(?:require|require_relative)\s+['"]([^'"]+)['"]/))
        "#{@type}:#{match[1]}"
      else
        "#{@type}:#{stripped}"
      end
    when :include, :extend, :using
      # Extract module name
      if (match = stripped.match(/^(?:include|extend|using)\s+(\S+)/))
        "#{@type}:#{match[1]}"
      else
        "#{@type}:#{stripped}"
      end
    when :autoload
      # Extract constant and path
      if (match = stripped.match(/^autoload\s+:?(\w+)/))
        "#{@type}:#{match[1]}"
      else
        "#{@type}:#{stripped}"
      end
    else
      "#{@type}:#{stripped}"
    end
  end
end

#to_linesObject

Returns lines as an array (for reconstruction)



50
51
52
53
54
# File 'lib/isort/import_statement.rb', line 50

def to_lines
  result = @leading_comments.dup
  result << @raw_line
  result
end

#to_sObject

Returns the full representation including leading comments



42
43
44
45
46
47
# File 'lib/isort/import_statement.rb', line 42

def to_s
  lines = []
  lines.concat(@leading_comments) unless @leading_comments.empty?
  lines << @raw_line
  lines.join
end