Class: Appydave::Tools::Jump::Location

Inherits:
Object
  • Object
show all
Defined in:
lib/appydave/tools/jump/location.rb

Overview

Note:

git_remote is TRI-STATE and #to_h preserves all three cases: a URL string (has a remote), an explicit nil (a git repo with no remote backup), and the key being absent entirely (not a git repo). Do not collapse nil into absent — they mean different things.

Location represents a single development folder location

Examples:

Creating a location

location = Location.new(
  key: 'ad-tools',
  path: '~/dev/ad/appydave-tools',
  jump: 'jad-tools',
  brand: 'appydave',
  type: 'tool',
  tags: ['ruby', 'cli'],
  description: 'AppyDave CLI tools'
)

Constant Summary collapse

VALID_KEY_PATTERN =
/\A[a-z0-9][a-z0-9-]*[a-z0-9]\z|\A[a-z0-9]\z/.freeze
VALID_PATH_PATTERN =
%r{\A[~/]}.freeze
VALID_TAG_PATTERN =
/\A[a-z0-9][a-z0-9-]*[a-z0-9]\z|\A[a-z0-9]\z/.freeze

Instance Attribute Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(attrs = {}) ⇒ Location

Returns a new instance of Location.



31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
# File 'lib/appydave/tools/jump/location.rb', line 31

def initialize(attrs = {})
  attrs = normalize_attrs(attrs)

  @key = attrs[:key]
  @path = attrs[:path]
  @jump = attrs[:jump] || default_jump
  @brand = attrs[:brand]
  @client = attrs[:client]
  @type = attrs[:type]
  @status = attrs[:status]
  @tags = Array(attrs[:tags])
  @description = attrs[:description]
  @git_remote = attrs[:git_remote]
  @context = attrs[:context]
  @notes = attrs[:notes]

  # git_remote distinguishes "explicit nil" from "not supplied"
  @git_remote_given = attrs.key?(:git_remote)
end

Instance Attribute Details

#brandObject (readonly)

Returns the value of attribute brand.



28
29
30
# File 'lib/appydave/tools/jump/location.rb', line 28

def brand
  @brand
end

#clientObject (readonly)

Returns the value of attribute client.



28
29
30
# File 'lib/appydave/tools/jump/location.rb', line 28

def client
  @client
end

#contextObject (readonly)

Returns the value of attribute context.



28
29
30
# File 'lib/appydave/tools/jump/location.rb', line 28

def context
  @context
end

#descriptionObject (readonly)

Returns the value of attribute description.



28
29
30
# File 'lib/appydave/tools/jump/location.rb', line 28

def description
  @description
end

#git_remoteObject (readonly)

Returns the value of attribute git_remote.



28
29
30
# File 'lib/appydave/tools/jump/location.rb', line 28

def git_remote
  @git_remote
end

#jumpObject (readonly)

Returns the value of attribute jump.



28
29
30
# File 'lib/appydave/tools/jump/location.rb', line 28

def jump
  @jump
end

#keyObject (readonly)

Returns the value of attribute key.



28
29
30
# File 'lib/appydave/tools/jump/location.rb', line 28

def key
  @key
end

#notesObject (readonly)

Returns the value of attribute notes.



28
29
30
# File 'lib/appydave/tools/jump/location.rb', line 28

def notes
  @notes
end

#pathObject (readonly)

Returns the value of attribute path.



28
29
30
# File 'lib/appydave/tools/jump/location.rb', line 28

def path
  @path
end

#statusObject (readonly)

Returns the value of attribute status.



28
29
30
# File 'lib/appydave/tools/jump/location.rb', line 28

def status
  @status
end

#tagsObject (readonly)

Returns the value of attribute tags.



28
29
30
# File 'lib/appydave/tools/jump/location.rb', line 28

def tags
  @tags
end

#typeObject (readonly)

Returns the value of attribute type.



28
29
30
# File 'lib/appydave/tools/jump/location.rb', line 28

def type
  @type
end

Instance Method Details

#git_remote_given?Boolean

Was git_remote supplied at all (even as nil)?

Returns:

  • (Boolean)


54
55
56
# File 'lib/appydave/tools/jump/location.rb', line 54

def git_remote_given?
  @git_remote_given
end

#searchable_terms(brands: {}, clients: {}) ⇒ Array<String>

Get all searchable text for this location

Parameters:

  • brands (Hash) (defaults to: {})

    Brand definitions with aliases

  • clients (Hash) (defaults to: {})

    Client definitions with aliases

Returns:

  • (Array<String>)

    All searchable terms



111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
# File 'lib/appydave/tools/jump/location.rb', line 111

def searchable_terms(brands: {}, clients: {})
  terms = [key, path, type, description].compact
  terms.concat(tags)

  # Add brand and its aliases
  if brand && brands[brand]
    terms << brand
    terms.concat(Array(brands[brand]['aliases'] || brands[brand][:aliases]))
  elsif brand
    terms << brand
  end

  # Add client and its aliases
  if client && clients[client]
    terms << client
    terms.concat(Array(clients[client]['aliases'] || clients[client][:aliases]))
  elsif client
    terms << client
  end

  terms.compact.map(&:to_s).map(&:downcase)
end

#to_hHash

Convert to hash for JSON serialization

Key order matches the on-disk locations.json convention so round-tripping an entry produces a minimal diff.

Returns:

  • (Hash)


84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
# File 'lib/appydave/tools/jump/location.rb', line 84

def to_h
  hash = {
    key: key,
    path: path,
    jump: jump,
    brand: brand,
    client: client,
    type: type,
    status: status,
    tags: tags,
    description: description
  }.compact

  # Preserve the tri-state: an explicit nil means "git repo, no remote"
  # and must survive; an absent key means "not a git repo".
  hash[:git_remote] = git_remote if git_remote_given?

  hash[:context] = context if context
  hash[:notes] = notes if notes
  hash
end

#valid?Boolean

Check if location is valid

Returns:

  • (Boolean)


74
75
76
# File 'lib/appydave/tools/jump/location.rb', line 74

def valid?
  validate.empty?
end

#validateArray<String>

Validate the location

Returns:

  • (Array<String>)

    List of validation errors (empty if valid)



61
62
63
64
65
66
67
68
69
# File 'lib/appydave/tools/jump/location.rb', line 61

def validate
  errors = []
  errors << 'Key is required' if key.nil? || key.empty?
  errors << "Key '#{key}' is invalid (must be lowercase alphanumeric with hyphens)" if key && !valid_key?
  errors << 'Path is required' if path.nil? || path.empty?
  errors << "Path '#{path}' is invalid (must start with ~ or /)" if path && !valid_path?
  errors.concat(validate_tags)
  errors
end