16007: Account for all the edges. still wip.
[arvados.git] / services / api / app / models / user.rb
index 8ab8ea1d85b0146f692993a8cd1fb6199addc8fc..6dce3a42e0abe324a752f5f54bffbe5e8138f675 100644 (file)
@@ -3,13 +3,13 @@
 # SPDX-License-Identifier: AGPL-3.0
 
 require 'can_be_an_owner'
-require 'refresh_permission_view'
 
 class User < ArvadosModel
   include HasUuid
   include KindAndEtag
   include CommonApiTemplate
   include CanBeAnOwner
+  extend CurrentApiClient
 
   serialize :prefs, Hash
   has_many :api_client_authorizations
@@ -20,6 +20,7 @@ class User < ArvadosModel
             },
             uniqueness: true,
             allow_nil: true)
+  validate :must_unsetup_to_deactivate
   before_update :prevent_privilege_escalation
   before_update :prevent_inactive_admin
   before_update :verify_repositories_empty, :if => Proc.new { |user|
@@ -30,15 +31,16 @@ class User < ArvadosModel
   before_create :set_initial_username, :if => Proc.new { |user|
     user.username.nil? and user.email
   }
+  after_create :update_permissions
   after_create :setup_on_activate
   after_create :add_system_group_permission_link
-  after_create :invalidate_permissions_cache
   after_create :auto_setup_new_user, :if => Proc.new { |user|
     Rails.configuration.Users.AutoSetupNewUsers and
     (user.uuid != system_user_uuid) and
     (user.uuid != anonymous_user_uuid)
   }
   after_create :send_admin_notifications
+  after_update :update_permissions, :if => :owner_uuid_changed?
   after_update :send_profile_created_notification
   after_update :sync_repository_names, :if => Proc.new { |user|
     (user.uuid != system_user_uuid) and
@@ -46,6 +48,7 @@ class User < ArvadosModel
     (not user.username_was.nil?)
   }
 
+
   has_many :authorized_keys, :foreign_key => :authorized_user_uuid, :primary_key => :uuid
   has_many :repositories, foreign_key: :owner_uuid, primary_key: :uuid
 
@@ -75,6 +78,12 @@ class User < ArvadosModel
      {read: true, write: true},
      {read: true, write: true, manage: true}]
 
+  VAL_FOR_PERM =
+    {:read => 1,
+     :write => 2,
+     :manage => 3}
+
+
   def full_name
     "#{first_name} #{last_name}".strip
   end
@@ -86,7 +95,7 @@ class User < ArvadosModel
   end
 
   def groups_i_can(verb)
-    my_groups = self.group_permissions.select { |uuid, mask| mask[verb] }.keys
+    my_groups = self.group_permissions(VAL_FOR_PERM[verb]).keys
     if verb == :read
       my_groups << anonymous_group_uuid
     end
@@ -105,60 +114,244 @@ class User < ArvadosModel
         end
       end
       next if target_uuid == self.uuid
-      next if (group_permissions[target_uuid] and
-               group_permissions[target_uuid][action])
-      if target.respond_to? :owner_uuid
-        next if target.owner_uuid == self.uuid
-        next if (group_permissions[target.owner_uuid] and
-                 group_permissions[target.owner_uuid][action])
-      end
-      sufficient_perms = case action
-                         when :manage
-                           ['can_manage']
-                         when :write
-                           ['can_manage', 'can_write']
-                         when :read
-                           ['can_manage', 'can_write', 'can_read']
-                         else
-                           # (Skip this kind of permission opportunity
-                           # if action is an unknown permission type)
-                         end
-      if sufficient_perms
-        # Check permission links with head_uuid pointing directly at
-        # the target object. If target is a Group, this is redundant
-        # and will fail except [a] if permission caching is broken or
-        # [b] during a race condition, where a permission link has
-        # *just* been added.
-        if Link.where(link_class: 'permission',
-                      name: sufficient_perms,
-                      tail_uuid: groups_i_can(action) + [self.uuid],
-                      head_uuid: target_uuid).any?
-          next
-        end
+
+      target_owner_uuid = target.owner_uuid if target.respond_to? :owner_uuid
+
+      unless ActiveRecord::Base.connection.
+        exec_query(%{
+SELECT 1 FROM #{PERMISSION_VIEW}
+  WHERE user_uuid = $1 and
+        ((target_uuid = $2 and perm_level >= $3)
+         or (target_uuid = $4 and perm_level >= $3 and traverse_owned))
+},
+                  # "name" arg is a query label that appears in logs:
+                   "user_can_query",
+                   [[nil, self.uuid],
+                    [nil, target_uuid],
+                    [nil, VAL_FOR_PERM[action]],
+                    [nil, target_owner_uuid]]
+                  ).any?
+        return false
       end
-      return false
     end
     true
   end
 
-  def self.invalidate_permissions_cache(async=false)
-    refresh_permission_view(async)
+  def update_permissions
+
+#       puts "Update permissions for #{uuid}"
+#     User.printdump %{
+# select * from materialized_permissions where user_uuid='#{uuid}'
+# }
+#     puts "---"
+    User.update_permissions self.owner_uuid, self.uuid, 3
+
+#   puts "post-update"
+#    User.printdump %{
+# select * from materialized_permissions where user_uuid='#{uuid}'
+# }
+#    puts "<<<"
   end
 
-  def invalidate_permissions_cache
-    User.invalidate_permissions_cache
+  def self.printdump qr
+    q1 = ActiveRecord::Base.connection.exec_query qr
+    q1.each do |r|
+      puts r
+    end
+  end
+
+  def recompute_permissions
+    ActiveRecord::Base.connection.execute("DELETE FROM #{PERMISSION_VIEW} where user_uuid='#{uuid}'")
+    ActiveRecord::Base.connection.execute %{
+INSERT INTO #{PERMISSION_VIEW}
+select '#{uuid}', g.target_uuid, g.val, g.traverse_owned
+from search_permission_graph('#{uuid}', 3) as g
+}
+  end
+
+  def self.update_permissions perm_origin_uuid, starting_uuid, perm_level
+    # Update a subset of the permission graph
+    # perm_level is the inherited permission
+    # perm_level is a number from 0-3
+    #   can_read=1
+    #   can_write=2
+    #   can_manage=3
+    #   call with perm_level=0 to revoke permissions
+    #
+    # 1. Compute set (group, permission) implied by traversing
+    #    graph starting at this group
+    # 2. Find links from outside the graph that point inside
+    # 3. For each starting uuid, get the set of permissions from the
+    #    materialized permission table
+    # 3. Delete permissions from table not in our computed subset.
+    # 4. Upsert each permission in our subset (user, group, val)
+
+    ## testinging
+    puts "\n__ update_permissions __"
+#     puts "What's in there now for #{starting_uuid}"
+#     printdump %{
+# select * from materialized_permissions where user_uuid='#{starting_uuid}'
+# }
+
+    puts "search_permission_graph #{perm_origin_uuid} #{starting_uuid}, #{perm_level}"
+    printdump %{
+select '#{perm_origin_uuid}'::varchar as perm_origin_uuid, target_uuid, val, traverse_owned from search_permission_graph('#{starting_uuid}', #{perm_level})
+}
+
+#     puts "other_links #{perm_origin_uuid} #{starting_uuid}, #{perm_level}"
+#     printdump %{
+# with
+# perm_from_start(perm_origin_uuid, target_uuid, val, traverse_owned) as (
+#   select '#{perm_origin_uuid}'::varchar, target_uuid, val, traverse_owned
+#     from search_permission_graph('#{starting_uuid}'::varchar, #{perm_level}))
+
+#     select links.tail_uuid as perm_origin_uuid, links.head_uuid, links.name
+#       from links
+#       where links.link_class='permission' and
+#         links.tail_uuid not in (select target_uuid from perm_from_start where traverse_owned) and
+#         links.tail_uuid != '#{perm_origin_uuid}' and
+#         links.head_uuid in (select target_uuid from perm_from_start)
+# }
+
+    puts "additional_perms #{perm_origin_uuid} #{starting_uuid}, #{perm_level}"
+    printdump %{
+with
+perm_from_start(perm_origin_uuid, target_uuid, val, traverse_owned) as (
+  select '#{perm_origin_uuid}'::varchar, target_uuid, val, traverse_owned
+    from search_permission_graph('#{starting_uuid}'::varchar, #{perm_level})),
+
+  edges(tail_uuid, head_uuid, val) as (
+        select * from permission_graph_edges()),
+
+  additional_perms(perm_origin_uuid, target_uuid, val, traverse_owned) as (
+    select edges.tail_uuid as perm_origin_uuid, ps.target_uuid, ps.val,
+           should_traverse_owned(ps.target_uuid, ps.val)
+      from edges, lateral search_permission_graph(edges.head_uuid, edges.val) as ps
+      where (not (edges.tail_uuid = '#{perm_origin_uuid}' and
+                  edges.head_uuid = '#{starting_uuid}' and
+                  edges.val = #{perm_level})) and
+            edges.tail_uuid not in (select target_uuid from perm_from_start) and
+            edges.head_uuid in (select target_uuid from perm_from_start)),
+
+  partial_perms(perm_origin_uuid, target_uuid, val, traverse_owned) as (
+      select * from perm_from_start
+    union
+      select * from additional_perms
+  ),
+
+  user_identity_perms(perm_origin_uuid, target_uuid, val, traverse_owned) as (
+    select users.uuid as perm_origin_uuid, ps.target_uuid, ps.val, ps.traverse_owned
+      from users, lateral search_permission_graph(users.uuid, 3) as ps
+      where users.owner_uuid not in (select target_uuid from partial_perms where traverse_owned) and
+      users.uuid in (select target_uuid from partial_perms)
+  ),
+
+  all_perms(perm_origin_uuid, target_uuid, val, traverse_owned) as (
+      select * from additional_perms
+    union
+      select * from user_identity_perms
+  )
+
+  select * from all_perms order by perm_origin_uuid, target_uuid
+}
+
+    puts "Perms out"
+    printdump %{
+select * from compute_permission_subgraph('#{perm_origin_uuid}', '#{starting_uuid}', '#{perm_level}')
+order by user_uuid, target_uuid
+}
+    ## end
+
+    temptable_perms = "temp_perms_#{rand(2**64).to_s(10)}"
+    ActiveRecord::Base.connection.exec_query %{
+create temporary table #{temptable_perms} on commit drop
+as select * from compute_permission_subgraph($1, $2, $3)
+},
+                                             'Group.search_permissions',
+                                             [[nil, perm_origin_uuid],
+                                              [nil, starting_uuid],
+                                              [nil, perm_level]]
+
+#     q1 = ActiveRecord::Base.connection.exec_query %{
+# select * from #{temptable_perms} order by user_uuid, target_uuid
+# }
+#     puts "recomputed perms was #{perm_origin_uuid} #{starting_uuid}, #{perm_level}"
+#     q1.each do |r|
+#       puts r
+#     end
+#     puts "<<<<"
+
+    ActiveRecord::Base.connection.exec_query %{
+delete from materialized_permissions where
+  target_uuid in (select target_uuid from #{temptable_perms}) and
+  (user_uuid not in (select user_uuid from #{temptable_perms} where target_uuid=materialized_permissions.target_uuid)
+   or user_uuid in (select user_uuid from #{temptable_perms} where target_uuid=materialized_permissions.target_uuid and perm_level=0))
+}
+
+    ActiveRecord::Base.connection.exec_query %{
+insert into materialized_permissions (user_uuid, target_uuid, perm_level, traverse_owned)
+  select user_uuid, target_uuid, val as perm_level, traverse_owned from #{temptable_perms}
+on conflict (user_uuid, target_uuid) do update set perm_level=EXCLUDED.perm_level, traverse_owned=EXCLUDED.traverse_owned;
+}
+
+    # for testing only - make a copy of the table and compare it to the one generated
+    # using a full permission recompute
+
+#      puts "dump--"
+#      User.printdump %{
+#  select * from users
+#      }
+#      User.printdump %{
+#  select * from groups
+#      }
+#      User.printdump %{
+# select * from search_permission_graph('zzzzz-tpzed-000000000000000', 3)
+#      }
+#      puts "--"
+
+
+    q1 = ActiveRecord::Base.connection.exec_query %{
+select user_uuid, target_uuid, perm_level, traverse_owned from materialized_permissions
+order by user_uuid, target_uuid
+}
+
+    q2 = ActiveRecord::Base.connection.exec_query %{
+select users.uuid as user_uuid, g.target_uuid, g.val as perm_level, g.traverse_owned
+from users, lateral search_permission_graph(users.uuid, 3) as g where g.val > 0
+order by users.uuid, target_uuid
+}
+
+    if q1.count != q2.count
+      puts "Didn't match incremental+: #{q1.count} != full refresh-: #{q2.count}"
+    end
+
+    if q1.count > q2.count
+      q1.each_with_index do |r, i|
+        if r != q2[i]
+          puts "+#{r}\n-#{q2[i]}"
+          raise "Didn't match"
+        end
+      end
+    else
+      q2.each_with_index do |r, i|
+        if r != q1[i]
+          puts "+#{q1[i]}\n-#{r}"
+          raise "Didn't match"
+        end
+      end
+    end
   end
 
   # Return a hash of {user_uuid: group_perms}
   def self.all_group_permissions
     all_perms = {}
     ActiveRecord::Base.connection.
-      exec_query("SELECT user_uuid, target_owner_uuid, perm_level, trashed
+      exec_query("SELECT user_uuid, target_uuid, perm_level
                   FROM #{PERMISSION_VIEW}
-                  WHERE target_owner_uuid IS NOT NULL",
+                  WHERE traverse_owned",
                   # "name" arg is a query label that appears in logs:
-                  "all_group_permissions",
-                  ).rows.each do |user_uuid, group_uuid, max_p_val, trashed|
+                 "all_group_permissions").
+      rows.each do |user_uuid, group_uuid, max_p_val|
       all_perms[user_uuid] ||= {}
       all_perms[user_uuid][group_uuid] = PERMS_FOR_VAL[max_p_val.to_i]
     end
@@ -168,36 +361,40 @@ class User < ArvadosModel
   # Return a hash of {group_uuid: perm_hash} where perm_hash[:read]
   # and perm_hash[:write] are true if this user can read and write
   # objects owned by group_uuid.
-  def group_permissions
-    group_perms = {self.uuid => {:read => true, :write => true, :manage => true}}
+  def group_permissions(level=1)
+    group_perms = {}
     ActiveRecord::Base.connection.
-      exec_query("SELECT target_owner_uuid, perm_level, trashed
-                  FROM #{PERMISSION_VIEW}
-                  WHERE user_uuid = $1
-                  AND target_owner_uuid IS NOT NULL",
+      exec_query(%{
+SELECT target_uuid, perm_level
+  FROM #{PERMISSION_VIEW}
+  WHERE user_uuid = $1 and perm_level >= $2
+},
                   # "name" arg is a query label that appears in logs:
-                  "group_permissions for #{uuid}",
+                  "group_permissions_for_user",
                   # "binds" arg is an array of [col_id, value] for '$1' vars:
-                  [[nil, uuid]],
-                ).rows.each do |group_uuid, max_p_val, trashed|
+                  [[nil, uuid],
+                   [nil, level]]).
+      rows.each do |group_uuid, max_p_val|
       group_perms[group_uuid] = PERMS_FOR_VAL[max_p_val.to_i]
     end
     group_perms
   end
 
   # create links
-  def setup(openid_prefix:, repo_name: nil, vm_uuid: nil)
-    oid_login_perm = create_oid_login_perm openid_prefix
+  def setup(repo_name: nil, vm_uuid: nil)
     repo_perm = create_user_repo_link repo_name
     vm_login_perm = create_vm_login_permission_link(vm_uuid, username) if vm_uuid
     group_perm = create_user_group_link
 
-    return [oid_login_perm, repo_perm, vm_login_perm, group_perm, self].compact
+    return [repo_perm, vm_login_perm, group_perm, self].compact
   end
 
   # delete user signatures, login, repo, and vm perms, and mark as inactive
   def unsetup
     # delete oid_login_perms for this user
+    #
+    # note: these permission links are obsolete, they have no effect
+    # on anything and they are not created for new users.
     Link.where(tail_uuid: self.email,
                      link_class: 'permission',
                      name: 'can_login').destroy_all
@@ -233,6 +430,37 @@ class User < ArvadosModel
     self.save!
   end
 
+  def must_unsetup_to_deactivate
+    if self.is_active_changed? &&
+       self.is_active_was == true &&
+       !self.is_active
+
+      group = Group.where(name: 'All users').select do |g|
+        g[:uuid].match(/-f+$/)
+      end.first
+
+      # When a user is set up, they are added to the "All users"
+      # group.  A user that is part of the "All users" group is
+      # allowed to self-activate.
+      #
+      # It doesn't make sense to deactivate a user (set is_active =
+      # false) without first removing them from the "All users" group,
+      # because they would be able to immediately reactivate
+      # themselves.
+      #
+      # The 'unsetup' method removes the user from the "All users"
+      # group (and also sets is_active = false) so send a message
+      # explaining the correct way to deactivate a user.
+      #
+      if Link.where(tail_uuid: self.uuid,
+                    head_uuid: group[:uuid],
+                    link_class: 'permission',
+                    name: 'can_read').any?
+        errors.add :is_active, "cannot be set to false directly, use the 'Deactivate' button on Workbench, or the 'unsetup' API call"
+      end
+    end
+  end
+
   def set_initial_username(requested: false)
     if !requested.is_a?(String) || requested.empty?
       email_parts = email.partition("@")
@@ -271,45 +499,87 @@ class User < ArvadosModel
     end
   end
 
-  # Move this user's (i.e., self's) owned items into new_owner_uuid.
-  # Also redirect future uses of this account to
-  # redirect_to_user_uuid, i.e., when a caller authenticates to this
-  # account in the future, the account redirect_to_user_uuid account
-  # will be used instead.
+  # Move this user's (i.e., self's) owned items to new_owner_uuid and
+  # new_user_uuid (for things normally owned directly by the user).
+  #
+  # If redirect_auth is true, also reassign auth tokens and ssh keys,
+  # and redirect this account to redirect_to_user_uuid, i.e., when a
+  # caller authenticates to this account in the future, the account
+  # redirect_to_user_uuid account will be used instead.
   #
   # current_user must have admin privileges, i.e., the caller is
   # responsible for checking permission to do this.
-  def merge(new_owner_uuid:, redirect_to_user_uuid:)
+  def merge(new_owner_uuid:, new_user_uuid:, redirect_to_new_user:)
     raise PermissionDeniedError if !current_user.andand.is_admin
-    raise "not implemented" if !redirect_to_user_uuid
+    raise "Missing new_owner_uuid" if !new_owner_uuid
+    raise "Missing new_user_uuid" if !new_user_uuid
     transaction(requires_new: true) do
       reload
       raise "cannot merge an already merged user" if self.redirect_to_user_uuid
 
-      new_user = User.where(uuid: redirect_to_user_uuid).first
+      new_user = User.where(uuid: new_user_uuid).first
       raise "user does not exist" if !new_user
       raise "cannot merge to an already merged user" if new_user.redirect_to_user_uuid
 
-      # Existing API tokens are updated to authenticate to the new
-      # user.
-      ApiClientAuthorization.
-        where(user_id: id).
-        update_all(user_id: new_user.id)
+      # If 'self' is a remote user, don't transfer authorizations
+      # (i.e. ability to access the account) to the new user, because
+      # that gives the remote site the ability to access the 'new'
+      # user account that takes over the 'self' account.
+      #
+      # If 'self' is a local user, it is okay to transfer
+      # authorizations, even if the 'new' user is a remote account,
+      # because the remote site does not gain the ability to access an
+      # account it could not before.
+
+      if redirect_to_new_user and self.uuid[0..4] == Rails.configuration.ClusterID
+        # Existing API tokens and ssh keys are updated to authenticate
+        # to the new user.
+        ApiClientAuthorization.
+          where(user_id: id).
+          update_all(user_id: new_user.id)
+
+        user_updates = [
+          [AuthorizedKey, :owner_uuid],
+          [AuthorizedKey, :authorized_user_uuid],
+          [Link, :owner_uuid],
+          [Link, :tail_uuid],
+          [Link, :head_uuid],
+        ]
+      else
+        # Destroy API tokens and ssh keys associated with the old
+        # user.
+        ApiClientAuthorization.where(user_id: id).destroy_all
+        AuthorizedKey.where(owner_uuid: uuid).destroy_all
+        AuthorizedKey.where(authorized_user_uuid: uuid).destroy_all
+        user_updates = [
+          [Link, :owner_uuid],
+          [Link, :tail_uuid]
+        ]
+      end
 
       # References to the old user UUID in the context of a user ID
       # (rather than a "home project" in the project hierarchy) are
       # updated to point to the new user.
-      [
-        [AuthorizedKey, :owner_uuid],
-        [AuthorizedKey, :authorized_user_uuid],
-        [Repository, :owner_uuid],
-        [Link, :owner_uuid],
-        [Link, :tail_uuid],
-        [Link, :head_uuid],
-      ].each do |klass, column|
+      user_updates.each do |klass, column|
         klass.where(column => uuid).update_all(column => new_user.uuid)
       end
 
+      # Need to update repository names to new username
+      if username
+        old_repo_name_re = /^#{Regexp.escape(username)}\//
+        Repository.where(:owner_uuid => uuid).each do |repo|
+          repo.owner_uuid = new_user.uuid
+          repo_name_sub = "#{new_user.username}/"
+          name = repo.name.sub(old_repo_name_re, repo_name_sub)
+          while (conflict = Repository.where(:name => name).first) != nil
+            repo_name_sub += "migrated"
+            name = repo.name.sub(old_repo_name_re, repo_name_sub)
+          end
+          repo.name = name
+          repo.save!
+        end
+      end
+
       # References to the merged user's "home project" are updated to
       # point to new_owner_uuid.
       ActiveRecord::Base.descendants.reject(&:abstract_class?).each do |klass|
@@ -322,8 +592,11 @@ class User < ArvadosModel
         klass.where(owner_uuid: uuid).update_all(owner_uuid: new_owner_uuid)
       end
 
-      update_attributes!(redirect_to_user_uuid: new_user.uuid)
-      invalidate_permissions_cache
+      if redirect_to_new_user
+        update_attributes!(redirect_to_user_uuid: new_user.uuid, username: nil)
+      end
+      self.recompute_permissions
+      new_user.recompute_permissions
     end
   end
 
@@ -331,10 +604,12 @@ class User < ArvadosModel
     user = self
     redirects = 0
     while (uuid = user.redirect_to_user_uuid)
-      user = User.unscoped.find_by_uuid(uuid)
-      if !user
-        raise Exception.new("user uuid #{user.uuid} redirects to nonexistent uuid #{uuid}")
+      break if uuid.empty?
+      nextuser = User.unscoped.find_by_uuid(uuid)
+      if !nextuser
+        raise Exception.new("user uuid #{user.uuid} redirects to nonexistent uuid '#{uuid}'")
       end
+      user = nextuser
       redirects += 1
       if redirects > 15
         raise "Starting from #{self.uuid} redirect_to_user_uuid exceeded maximum number of redirects"
@@ -354,8 +629,6 @@ class User < ArvadosModel
     #   alternate_emails
     #   identity_url
 
-    info = info.with_indifferent_access
-
     primary_user = nil
 
     # local database
@@ -381,7 +654,7 @@ class User < ArvadosModel
         if !primary_user
           primary_user = user.redirects_to
         elsif primary_user.uuid != user.redirects_to.uuid
-          raise "Ambigious email address, directs to both #{primary_user.uuid} and #{user.redirects_to.uuid}"
+          raise "Ambiguous email address, directs to both #{primary_user.uuid} and #{user.redirects_to.uuid}"
         end
       end
     end
@@ -392,7 +665,7 @@ class User < ArvadosModel
                               :is_admin => false,
                               :is_active => Rails.configuration.Users.NewUsersAreActive)
 
-      primary_user.set_initial_username(requested: info['username']) if info['username']
+      primary_user.set_initial_username(requested: info['username']) if info['username'] && !info['username'].blank?
       primary_user.identity_url = info['identity_url'] if identity_url
     end
 
@@ -534,30 +807,6 @@ class User < ArvadosModel
     merged
   end
 
-  def create_oid_login_perm(openid_prefix)
-    # Check oid_login_perm
-    oid_login_perms = Link.where(tail_uuid: self.email,
-                                 head_uuid: self.uuid,
-                                 link_class: 'permission',
-                                 name: 'can_login')
-
-    if !oid_login_perms.any?
-      # create openid login permission
-      oid_login_perm = Link.create!(link_class: 'permission',
-                                   name: 'can_login',
-                                   tail_uuid: self.email,
-                                   head_uuid: self.uuid,
-                                   properties: {
-                                     "identity_url_prefix" => openid_prefix,
-                                   })
-      logger.info { "openid login permission: " + oid_login_perm[:uuid] }
-    else
-      oid_login_perm = oid_login_perms.first
-    end
-
-    return oid_login_perm
-  end
-
   def create_user_repo_link(repo_name)
     # repo_name is optional
     if not repo_name
@@ -605,6 +854,7 @@ class User < ArvadosModel
 
   # add the user to the 'All users' group
   def create_user_group_link
+    #puts "In create_user_group_link"
     return (Link.where(tail_uuid: self.uuid,
                        head_uuid: all_users_group[:uuid],
                        link_class: 'permission',
@@ -639,13 +889,13 @@ class User < ArvadosModel
   def setup_on_activate
     return if [system_user_uuid, anonymous_user_uuid].include?(self.uuid)
     if is_active && (new_record? || is_active_changed?)
-      setup(openid_prefix: Rails.configuration.default_openid_prefix)
+      setup
     end
   end
 
   # Automatically setup new user during creation
   def auto_setup_new_user
-    setup(openid_prefix: Rails.configuration.default_openid_prefix)
+    setup
     if username
       create_vm_login_permission_link(Rails.configuration.Users.AutoSetupNewUsersWithVmUUID,
                                       username)