search.rb 4.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141
  1. # Copyright (C) 2012-2022 Zammad Foundation, https://zammad-foundation.org/
  2. class Organization
  3. module Search
  4. extend ActiveSupport::Concern
  5. # methods defined here are going to extend the class, not the instance of it
  6. class_methods do
  7. =begin
  8. search organizations preferences
  9. result = Organization.search_preferences(user_model)
  10. returns if user has permissions to search
  11. result = {
  12. prio: 1000,
  13. direct_search_index: true
  14. }
  15. returns if user has no permissions to search
  16. result = false
  17. =end
  18. def search_preferences(current_user)
  19. return false if !current_user.permissions?('ticket.agent') && !current_user.permissions?('admin.organization')
  20. {
  21. prio: 1500,
  22. direct_search_index: true,
  23. }
  24. end
  25. =begin
  26. search organizations
  27. result = Organization.search(
  28. current_user: User.find(123),
  29. query: 'search something',
  30. limit: 15,
  31. offset: 100,
  32. # sort single column
  33. sort_by: 'created_at',
  34. order_by: 'asc',
  35. # sort multiple columns
  36. sort_by: [ 'created_at', 'updated_at' ],
  37. order_by: [ 'asc', 'desc' ],
  38. )
  39. returns
  40. result = [organization_model1, organization_model2]
  41. =end
  42. def search(params)
  43. # get params
  44. query = params[:query]
  45. limit = params[:limit] || 10
  46. offset = params[:offset] || 0
  47. current_user = params[:current_user]
  48. sql_helper = ::SqlHelper.new(object: self)
  49. # check sort - positions related to order by
  50. sort_by = sql_helper.get_sort_by(params, %w[active updated_at])
  51. # check order - positions related to sort by
  52. order_by = sql_helper.get_order_by(params, %w[desc desc])
  53. # enable search only for agents and admins
  54. return [] if !search_preferences(current_user)
  55. # try search index backend
  56. if SearchIndexBackend.enabled?
  57. items = SearchIndexBackend.search(query, 'Organization', limit: limit,
  58. from: offset,
  59. sort_by: sort_by,
  60. order_by: order_by)
  61. organizations = []
  62. items.each do |item|
  63. organization = Organization.lookup(id: item[:id])
  64. next if !organization
  65. organizations.push organization
  66. end
  67. return organizations
  68. end
  69. order_select_sql = sql_helper.get_order_select(sort_by, order_by, 'organizations.updated_at')
  70. order_sql = sql_helper.get_order(sort_by, order_by, 'organizations.updated_at ASC')
  71. # fallback do sql query
  72. # - stip out * we already search for *query* -
  73. query.delete! '*'
  74. organizations = Organization.where_or_cis(%i[name note], "%#{query}%")
  75. .order(Arel.sql(order_sql))
  76. .offset(offset)
  77. .limit(limit)
  78. .to_a
  79. # use result independent of size if an explicit offset is given
  80. # this is the case for e.g. paginated searches
  81. return organizations if params[:offset].present?
  82. return organizations if organizations.length > 3
  83. # if only a few organizations are found, search for names of users
  84. organizations_by_user = Organization.select("DISTINCT(organizations.id), #{order_select_sql}")
  85. .joins('LEFT OUTER JOIN users ON users.organization_id = organizations.id')
  86. .where(User.or_cis(%i[firstname lastname email], "%#{query}%"))
  87. .order(Arel.sql(order_sql))
  88. .limit(limit)
  89. organizations_by_user.each do |organization_by_user|
  90. organization_exists = false
  91. organizations.each do |organization|
  92. next if organization.id != organization_by_user.id
  93. organization_exists = true
  94. break
  95. end
  96. # get model with full data
  97. next if organization_exists
  98. organizations.push Organization.find(organization_by_user.id)
  99. end
  100. organizations
  101. end
  102. end
  103. end
  104. end