Module: DurableHuggingfaceHub::Authentication

Defined in:
lib/durable_huggingface_hub/authentication.rb

Overview

Authentication methods for HuggingFace Hub.

This module provides methods for logging in and out of HuggingFace Hub, storing authentication tokens securely, and verifying credentials.

Class Method Summary collapse

Class Method Details

.git_available?Boolean

Checks if git is available on the system.

Returns:

  • (Boolean)

    True if git is available



125
126
127
# File 'lib/durable_huggingface_hub/authentication.rb', line 125

def self.git_available?
  system("which git > /dev/null 2>&1")
end

.logged_in?Boolean

Checks if a user is currently logged in (has a valid token).

Examples:

if DurableHuggingfaceHub.logged_in?
  puts "Already logged in"
end

Returns:

  • (Boolean)

    True if a token is available



115
116
117
118
# File 'lib/durable_huggingface_hub/authentication.rb', line 115

def self.logged_in?
  token = Utils::Auth.get_token
  !token.nil? && !token.empty?
end

.login(token: nil, add_to_git_credential: false) ⇒ String

Logs in to HuggingFace Hub and stores the authentication token.

If a token is provided, it will be validated and stored. If no token is provided and the process is running interactively, the user will be prompted to enter a token.

Examples:

With explicit token

DurableHuggingfaceHub.(token: "hf_...")

Interactive login

DurableHuggingfaceHub.  # Prompts for token

Login with git credential storage

DurableHuggingfaceHub.(token: "hf_...", add_to_git_credential: true)

Parameters:

  • token (String, nil) (defaults to: nil)

    Authentication token

  • add_to_git_credential (Boolean) (defaults to: false)

    Whether to add token to git credential helper

Returns:

  • (String)

    The stored token (masked)

Raises:



30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
# File 'lib/durable_huggingface_hub/authentication.rb', line 30

def self.(token: nil, add_to_git_credential: false)
  # Get token from parameter or prompt
  token = obtain_token(token)

  # Validate token format
  unless Utils::Auth.valid_token_format?(token)
    raise ValidationError.new("token", "Invalid token format. Token should start with 'hf_'")
  end

  # Verify token works by calling whoami
  begin
     = whoami(token: token)
  rescue HfHubHTTPError => e
    raise DurableHuggingfaceHubError.new("Login failed: #{e.message}")
  end

  # Store token
  Utils::Auth.write_token_to_file(token)

  # Store in git credential helper if requested
  if add_to_git_credential
    store_git_credential(token)
  end

  # Update configuration
  Configuration.instance.token = token

 # Return user info for CLI
  { name: .name, type: .type || "user" }
end

.logoutBoolean

Logs out of HuggingFace Hub by removing the stored token.

Returns:

  • (Boolean)

    True if token was removed, false if no token existed



67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
# File 'lib/durable_huggingface_hub/authentication.rb', line 67

def self.logout
  result = Utils::Auth.delete_token_file

  # Remove from git credential helper if present
  remove_git_credential

  # Clear from configuration
  Configuration.instance.token = nil

  if result
    puts "Logged out successfully. Token removed."
  else
    puts "No token found to remove."
  end

  result
end

.obtain_token(token) ⇒ String

Obtains a token either from parameter or by prompting the user.

Parameters:

  • token (String, nil)

    Provided token

Returns:

  • (String)

    Token

Raises:



192
193
194
195
196
197
198
199
200
201
202
203
204
205
# File 'lib/durable_huggingface_hub/authentication.rb', line 192

def self.obtain_token(token)
  return token if token && !token.empty?

    # Check if running interactively
    unless $stdin.respond_to?(:tty?) && $stdin.tty?
      raise DurableHuggingfaceHubError.new(
        "No token provided and not running interactively. " \
        "Please provide a token using the 'token' parameter."
      )
    end

  # Prompt for token
  prompt_for_token
end

.prompt_for_tokenString

Prompts the user to enter their authentication token.

The token input is hidden for security.

Returns:

  • (String)

    Entered token

Raises:



213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
# File 'lib/durable_huggingface_hub/authentication.rb', line 213

def self.prompt_for_token
  puts "\nTo login, you need a User Access Token from https://huggingface.co/settings/tokens"
  puts "You can create a new token or use an existing one."
  puts "\nPaste your token (input will be hidden):"

  # Read token without echoing to terminal
  begin
    if $stdin.respond_to?(:noecho) && $stdin.isatty
      token = $stdin.noecho(&:gets)&.chomp
    else
      # For testing or when noecho is not available
      token = $stdin.gets&.chomp
    end
  rescue Interrupt
    puts "\nLogin cancelled"
    raise DurableHuggingfaceHubError.new("Login cancelled by user")
  end

  if token.nil? || token.empty?
    raise DurableHuggingfaceHubError.new("Token entry cancelled or empty")
  end

  token
end

.remove_git_credentialBoolean

Returns True if removed successfully.

Returns:

  • (Boolean)

    True if removed successfully



160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
# File 'lib/durable_huggingface_hub/authentication.rb', line 160

def self.remove_git_credential
  # Check if git is available
  return false unless git_available?

  # First check if we have a stored token to know what to remove
  token = Utils::Auth.get_token
  return false unless token

  credential_data = <<~CREDENTIAL
    protocol=https
    host=huggingface.co
    username=hf_#{token[3..]}  # Extract token part after 'hf_'
  CREDENTIAL

  # Use git credential reject to remove the credential
  begin
    IO.popen("git credential reject", "w+") do |io|
      io.write(credential_data)
      io.close_write
      io.read # Consume any output
    end
    $?.success?
  rescue Errno::ENOENT, IOError
    false
  end
end

.store_git_credential(token) ⇒ Boolean

Stores the token in the git credential helper.

Parameters:

  • token (String)

    Authentication token

Returns:

  • (Boolean)

    True if stored successfully



133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
# File 'lib/durable_huggingface_hub/authentication.rb', line 133

def self.store_git_credential(token)
  # Check if git is available
  return false unless git_available?

  credential_data = <<~CREDENTIAL
    protocol=https
    host=huggingface.co
    username=hf_#{token[3..]}  # Extract token part after 'hf_'
    password=#{token}
  CREDENTIAL

  # Use git credential approve to store the credential
  begin
    IO.popen("git credential approve", "w+") do |io|
      io.write(credential_data)
      io.close_write
      io.read # Consume any output
    end
    $?.success?
  rescue Errno::ENOENT, IOError
    false
  end
end

.whoami(token: nil) ⇒ Hash

Returns information about the currently authenticated user.

Makes a request to the /api/whoami endpoint to retrieve user information.

Examples:

 = DurableHuggingfaceHub.whoami
puts ["name"]
puts ["fullname"]

Parameters:

  • token (String, nil) (defaults to: nil)

    Authentication token (uses stored token if not provided)

Returns:

  • (Hash)

    User information hash

Raises:



98
99
100
101
102
103
104
105
# File 'lib/durable_huggingface_hub/authentication.rb', line 98

def self.whoami(token: nil)
  token = Utils::Auth.get_token!(token: token)

  client = Utils::HttpClient.new(token: token)
  response = client.get("/api/whoami-v2")

  Types::User.from_hash(response.body)
end