diff --git a/app/models/ticket/overviews.rb b/app/models/ticket/overviews.rb index 406799456..1ea3e41f4 100644 --- a/app/models/ticket/overviews.rb +++ b/app/models/ticket/overviews.rb @@ -47,6 +47,8 @@ returns { overview: { id: 123, + name: 'some name', + view: 'some_view', updated_at: ..., }, count: 3, diff --git a/lib/search_index_backend.rb b/lib/search_index_backend.rb index f537c62d5..74ec1d2a3 100644 --- a/lib/search_index_backend.rb +++ b/lib/search_index_backend.rb @@ -481,25 +481,82 @@ get count of tickets and tickets which match on selector def self.selector2query(selector, _current_user, aggs_interval, limit) query_must = [] query_must_not = [] + relative_map = { + day: 'd', + year: 'y', + month: 'M', + hour: 'h', + minute: 'm', + } if selector.present? selector.each do |key, data| key_tmp = key.sub(/^.+?\./, '') t = {} - if data['value'].class == Array - t[:terms] = {} - t[:terms][key_tmp] = data['value'] + + # is/is not/contains/contains not + if data['operator'] == 'is' || data['operator'] == 'is not' || data['operator'] == 'contains' || data['operator'] == 'contains not' + if data['value'].class == Array + t[:terms] = {} + t[:terms][key_tmp] = data['value'] + else + t[:term] = {} + t[:term][key_tmp] = data['value'] + end + + # within last/within next (relative) + elsif data['operator'] == 'within last (relative)' || data['operator'] == 'within next (relative)' + range = relative_map[data['range'].to_sym] + if range.blank? + raise "Invalid relative_map for range '#{data['range']}'." + end + t[:range] = {} + t[:range][key_tmp] = {} + if data['operator'] == 'within last (relative)' + t[:range][key_tmp][:gte] = "now-#{data['value']}#{range}" + else + t[:range][key_tmp][:lt] = "now+#{data['value']}#{range}" + end + + # before/after (relative) + elsif data['operator'] == 'before (relative)' || data['operator'] == 'after (relative)' + range = relative_map[data['range'].to_sym] + if range.blank? + raise "Invalid relative_map for range '#{data['range']}'." + end + t[:range] = {} + t[:range][key_tmp] = {} + if data['operator'] == 'before (relative)' + t[:range][key_tmp][:lt] = "now-#{data['value']}#{range}" + else + t[:range][key_tmp][:gt] = "now+#{data['value']}#{range}" + end + + # before/after (absolute) + elsif data['operator'] == 'before (absolute)' || data['operator'] == 'after (absolute)' + t[:range] = {} + t[:range][key_tmp] = {} + if data['operator'] == 'before (absolute)' + t[:range][key_tmp][:lt] = (data['value']).to_s + else + t[:range][key_tmp][:gt] = (data['value']).to_s + end else - t[:term] = {} - t[:term][key_tmp] = data['value'] + raise "unknown operator '#{data['operator']}' for #{key}" end if data['operator'] == 'is' query_must.push t elsif data['operator'] == 'is not' query_must_not.push t elsif data['operator'] == 'contains' - query_must.push t + query_must_not.push t elsif data['operator'] == 'contains not' query_must_not.push t + elsif data['operator'] == 'within last (relative)' || data['operator'] == 'within next (relative)' + query_must.push t + elsif data['operator'] == 'before (relative)' || data['operator'] == 'after (relative)' + query_must.push t + elsif data['operator'] == 'before (absolute)' || data['operator'] == 'after (absolute)' + query_must.push t else raise "unknown operator '#{data['operator']}' for #{key}" end diff --git a/test/integration/report_test.rb b/test/integration/report_test.rb index 02d8c665a..4965f7990 100644 --- a/test/integration/report_test.rb +++ b/test/integration/report_test.rb @@ -251,6 +251,34 @@ class ReportTest < ActiveSupport::TestCase created_by_id: 1, ) + @ticket9 = Ticket.create!( + title: 'test 9', + group: group1, + customer_id: 2, + state: Ticket::State.lookup(name: 'open'), + priority: Ticket::Priority.lookup(name: '2 normal'), + close_at: '2037-11-02 12:30:00 UTC', + created_at: '2037-11-02 12:30:00 UTC', + updated_at: '2037-11-02 12:30:00 UTC', + updated_by_id: 1, + created_by_id: 1, + ) + Ticket::Article.create!( + ticket_id: @ticket9.id, + from: 'some_sender@example.com', + to: 'some_recipient@example.com', + subject: 'some subject', + message_id: 'some@id', + body: 'some message article_outbound', + internal: false, + sender: Ticket::Article::Sender.where(name: 'Agent').first, + type: Ticket::Article::Type.where(name: 'email').first, + created_at: '2037-11-02 12:30:00 UTC', + updated_at: '2037-11-02 12:30:00 UTC', + updated_by_id: 1, + created_by_id: 1, + ) + # execute background jobs Scheduler.worker(true) end @@ -968,6 +996,171 @@ class ReportTest < ActiveSupport::TestCase assert_equal(@ticket1.id, result[:ticket_ids][6].to_i) assert_nil(result[:ticket_ids][7]) + result = Report::TicketGenericTime.items( + range_start: '2015-01-01T00:00:00Z', + range_end: '2015-12-31T23:59:59Z', + selector: { + 'created_at' => { + 'operator' => 'before (absolute)', + 'value' => '2015-10-31T00:00:00Z' + } + }, # ticket selector to get only a collection of tickets + params: { field: 'created_at' }, + ) + + assert(result) + assert_equal(@ticket5.id, result[:ticket_ids][0].to_i) + assert_equal(@ticket4.id, result[:ticket_ids][1].to_i) + assert_equal(@ticket3.id, result[:ticket_ids][2].to_i) + assert_equal(@ticket2.id, result[:ticket_ids][3].to_i) + assert_equal(@ticket1.id, result[:ticket_ids][4].to_i) + assert_nil(result[:ticket_ids][5]) + + result = Report::TicketGenericTime.items( + range_start: '2015-01-01T00:00:00Z', + range_end: '2015-12-31T23:59:59Z', + selector: { + 'created_at' => { + 'operator' => 'after (absolute)', + 'value' => '2015-10-31T00:00:00Z' + } + }, # ticket selector to get only a collection of tickets + params: { field: 'created_at' }, + ) + + assert(result) + assert_equal(@ticket7.id, result[:ticket_ids][0].to_i) + assert_equal(@ticket6.id, result[:ticket_ids][1].to_i) + assert_nil(result[:ticket_ids][2]) + + result = Report::TicketGenericTime.items( + range_start: '2015-01-01T00:00:00Z', + range_end: '2015-12-31T23:59:59Z', + selector: { + 'created_at' => { + 'operator' => 'before (relative)', + 'range' => 'day', + 'value' => '1' + } + }, # ticket selector to get only a collection of tickets + params: { field: 'created_at' }, + ) + + result = Report::TicketGenericTime.items( + range_start: '2015-01-01T00:00:00Z', + range_end: '2015-12-31T23:59:59Z', + selector: { + 'created_at' => { + 'operator' => 'after (relative)', + 'range' => 'day', + 'value' => '1' + } + }, # ticket selector to get only a collection of tickets + params: { field: 'created_at' }, + ) + + assert(result) + assert_nil(result[:ticket_ids][0]) + + result = Report::TicketGenericTime.items( + range_start: '2037-01-01T00:00:00Z', + range_end: '2037-12-31T23:59:59Z', + selector: { + 'created_at' => { + 'operator' => 'before (relative)', + 'range' => 'day', + 'value' => '1' + } + }, # ticket selector to get only a collection of tickets + params: { field: 'created_at' }, + ) + + assert(result) + assert_nil(result[:ticket_ids][0]) + + result = Report::TicketGenericTime.items( + range_start: '2037-01-01T00:00:00Z', + range_end: '2037-12-31T23:59:59Z', + selector: { + 'created_at' => { + 'operator' => 'after (relative)', + 'range' => 'day', + 'value' => '5' + } + }, # ticket selector to get only a collection of tickets + params: { field: 'created_at' }, + ) + + assert(result) + assert_equal(@ticket9.id, result[:ticket_ids][0].to_i) + assert_nil(result[:ticket_ids][1]) + + result = Report::TicketGenericTime.items( + range_start: '2037-01-01T00:00:00Z', + range_end: '2037-12-31T23:59:59Z', + selector: { + 'created_at' => { + 'operator' => 'before (relative)', + 'range' => 'month', + 'value' => '1' + } + }, # ticket selector to get only a collection of tickets + params: { field: 'created_at' }, + ) + + assert(result) + assert_nil(result[:ticket_ids][0]) + + result = Report::TicketGenericTime.items( + range_start: '2037-01-01T00:00:00Z', + range_end: '2037-12-31T23:59:59Z', + selector: { + 'created_at' => { + 'operator' => 'after (relative)', + 'range' => 'month', + 'value' => '5' + } + }, # ticket selector to get only a collection of tickets + params: { field: 'created_at' }, + ) + + assert(result) + assert_equal(@ticket9.id, result[:ticket_ids][0].to_i) + assert_nil(result[:ticket_ids][1]) + + result = Report::TicketGenericTime.items( + range_start: '2037-01-01T00:00:00Z', + range_end: '2037-12-31T23:59:59Z', + selector: { + 'created_at' => { + 'operator' => 'before (relative)', + 'range' => 'year', + 'value' => '1' + } + }, # ticket selector to get only a collection of tickets + params: { field: 'created_at' }, + ) + + assert(result) + assert_nil(result[:ticket_ids][0]) + + result = Report::TicketGenericTime.items( + range_start: '2037-01-01T00:00:00Z', + range_end: '2037-12-31T23:59:59Z', + selector: { + 'created_at' => { + 'operator' => 'after (relative)', + 'range' => 'year', + 'value' => '5' + } + }, # ticket selector to get only a collection of tickets + params: { field: 'created_at' }, + ) + + assert(result) + assert_equal(@ticket9.id, result[:ticket_ids][0].to_i) + assert_nil(result[:ticket_ids][1]) + # cleanup Rake::Task['searchindex:drop'].execute end