2017-10-15 10 views
0

私はdatatablesを使って4列を表示しています。Rails 5 - 関連で重複して検索するクエリ

名前|カウント|最も近い支払期日|最も遅い期日。

私は最終的に表がしかし、それは今で照会する過ぎるに長い時間を取っていると私はそれだけに起因することの私のハック-N-スラッシュ法にだと信じて、(私は信じている)テストに基づいて、正しいデータを表示していますそれは働く。クエリはトランザクションポイントからきれいに見えますが、多くはあります。私は代わりに.join.pluckを利用しなければならないと信じていますが、私は正しい方法ではありません。

データを作成する私の機能です。 (ユーザーのアクティブなクライアントの-all-のリストである私はclients_resourceを送信initの。私は、簡潔にするために、インラインコメントを追加している。)

def data 
    clients.map do |client| 
     [ 
     ## The output is a link to the client, raw industry field, the number of 'tasks' they currently have 
     ## as noted in ##TASK_COUNT## 
     ## Then I want to link to the nearest TASK due date. (task_end_date) 
     ## This happened in ##TASK_END_DATE## 
     ## The final one is similar but finds the end_date withinj the Project 
     ## This is in ##PROJECT_END_DATE## 
     link_to(client.name, client), 
     client.industry, 
     client.status, 

     ##TASK_COUNT## 
     if client.tasks.present? ## My purpose here is to avoid 500 errors if a client has no tasks. Seemed like a hack 
      task = client.tasks.order(:task_start_date).first 
      project = Project.find(task.project_id) 
      link_to(client.tasks.count, url_helpers.project_tasks_path(project)) 
     else 
      client.tasks.count 
     end, 
     ##TASK_END_DATE## 
     if client.tasks.present? ## Again, hack method 
      task = client.tasks.order('task_end_date desc').first ## Exactly as it says - Was only way I could get the '' 
                  ## Typing this out I realize this logic is incorrect. It should return the NEAREST future task_end_date, but it is returning the furthest task_end_date, perior 
      project = task.project ## Was a hack to try to reduce the queries since the relationship will allow this query to work 
      #project = client.projects.order('end_date desc').first 
      if task.task_end_date.future? ## Hack to ensure the task_end_date is in the future other-wise it should print a warning 
      link_to(task.task_end_date.strftime("%B %e, %Y"), url_helpers.project_task_path(project, task)) 

      else 
       link_to("Is this project late?", url_helpers.project_tasks_path(client.nearest_project_id)) 
      end 
     else 
      'No Projects' 
     end, 
      ##PROJECT_END_DATE## 
     if client.tasks.present? && client.nearest_project_start.present? ##Hack to ensure it has tasks, and that the nearest_project_start has content. 
      project = Project.find(client.furthest_project_id) ## Gets the ProjectID for the furthest_project_id - This is handled by the model on save to help alliviate queries 
      link_to(project.end_date.strftime("%B %e, %Y"), url_helpers.project_task_path(project, client.furthest_project_id)) 
     else 
      'No Tasks Pending' 
     end 
     ] 
    end 
    end 

繰り返しますが、これは信じられないほど間違っを感じているが、私はわかりませんよどのようにそれを置くより良い。

また、3つのモデルERDのスニペットが役立つ場合もあります。

流れは

クライアントである - >プロジェクト - >タスク、だけでなく、バ​​ックアップに移動。 (したがってTask.first.clientはクライアントを返します)。

私はこれらのクエリをよりクリーンかつ正確にする方法を理解しようとしています。私は生のSQLをやっているだけですか?私はメソッドに加わるよりもはるかにSQLに優れています。

クエリ基本的にこれら〜20行は、私の懸念される

User Load (1.8ms) SELECT "users".* FROM "users" WHERE "users"."id" = $1 ORDER BY "users"."id" ASC LIMIT $2 [["id", 1], ["LIMIT", 1]] 
    (1.8ms) SELECT COUNT(*) FROM "clients" WHERE "clients"."user_id" = $1 AND (status != 'Not Active') AND (status != 'Suspended') [["user_id", 1]] 
    CACHE (0.4ms) SELECT COUNT(*) FROM "clients" WHERE "clients"."user_id" = $1 AND (status != 'Not Active') AND (status != 'Suspended') [["user_id", 1]] 
    Client Load (2.1ms) SELECT "clients".* FROM "clients" WHERE "clients"."user_id" = $1 AND (status != 'Not Active') AND (status != 'Suspended') ORDER BY name asc LIMIT $2 OFFSET $3 [["user_id", 1], ["LIMIT", 30], ["OFFSET", 0]] 
    Project Load (5.8ms) SELECT "projects".* FROM "projects" WHERE "projects"."client_id" IN (2, 1, 4, 3) 
    Task Load (2.1ms) SELECT "tasks".* FROM "tasks" WHERE "tasks"."project_id" IN (5, 6, 3, 4, 1, 7, 2) 
    Task Load (1.9ms) SELECT "tasks".* FROM "tasks" INNER JOIN "projects" ON "tasks"."project_id" = "projects"."id" WHERE "projects"."client_id" = $1 ORDER BY "tasks"."task_start_date" ASC LIMIT $2 [["client_id", 2], ["LIMIT", 1]] 
    Project Load (1.4ms) SELECT "projects".* FROM "projects" WHERE "projects"."id" = $1 LIMIT $2 [["id", 3], ["LIMIT", 1]] 
    (1.8ms) SELECT COUNT(*) FROM "tasks" INNER JOIN "projects" ON "tasks"."project_id" = "projects"."id" WHERE "projects"."client_id" = $1 [["client_id", 2]] 
    Task Load (4.1ms) SELECT "tasks".* FROM "tasks" INNER JOIN "projects" ON "tasks"."project_id" = "projects"."id" WHERE "projects"."client_id" = $1 ORDER BY task_end_date asc LIMIT $2 [["client_id", 2], ["LIMIT", 1]] 
    CACHE Project Load (0.4ms) SELECT "projects".* FROM "projects" WHERE "projects"."id" = $1 LIMIT $2 [["id", 3], ["LIMIT", 1]] 
    CACHE Project Load (0.5ms) SELECT "projects".* FROM "projects" WHERE "projects"."id" = $1 LIMIT $2 [["id", 3], ["LIMIT", 1]] 
    Task Load (2.0ms) SELECT "tasks".* FROM "tasks" INNER JOIN "projects" ON "tasks"."project_id" = "projects"."id" WHERE "projects"."client_id" = $1 ORDER BY "tasks"."task_start_date" ASC LIMIT $2 [["client_id", 1], ["LIMIT", 1]] 
    Project Load (1.5ms) SELECT "projects".* FROM "projects" WHERE "projects"."id" = $1 LIMIT $2 [["id", 1], ["LIMIT", 1]] 
    (1.8ms) SELECT COUNT(*) FROM "tasks" INNER JOIN "projects" ON "tasks"."project_id" = "projects"."id" WHERE "projects"."client_id" = $1 [["client_id", 1]] 
    Task Load (3.2ms) SELECT "tasks".* FROM "tasks" INNER JOIN "projects" ON "tasks"."project_id" = "projects"."id" WHERE "projects"."client_id" = $1 ORDER BY task_end_date asc LIMIT $2 [["client_id", 1], ["LIMIT", 1]] 
    CACHE Project Load (0.3ms) SELECT "projects".* FROM "projects" WHERE "projects"."id" = $1 LIMIT $2 [["id", 1], ["LIMIT", 1]] 
    CACHE Project Load (0.3ms) SELECT "projects".* FROM "projects" WHERE "projects"."id" = $1 LIMIT $2 [["id", 1], ["LIMIT", 1]] 
    (2.0ms) SELECT COUNT(*) FROM "tasks" INNER JOIN "projects" ON "tasks"."project_id" = "projects"."id" WHERE "projects"."client_id" = $1 [["client_id", 4]] 
Started GET "/clients" for 73.106.189.182 at 2017-10-15 01:18:19 +0000 
    Task Load (29.1ms) SELECT "tasks".* FROM "tasks" INNER JOIN "projects" ON "tasks"."project_id" = "projects"."id" WHERE "projects"."client_id" = $1 ORDER BY "tasks"."task_start_date" ASC LIMIT $2 [["client_id", 3], ["LIMIT", 1]] 
Cannot render console from 73.106.189.182! Allowed networks: 127.0.0.1, ::1, 127.0.0.0/127.255.255.255 
Processing by ClientsController#index as HTML 
    Project Load (45.9ms) SELECT "projects".* FROM "projects" WHERE "projects"."id" = $1 LIMIT $2 [["id", 2], ["LIMIT", 1]] 
    (11.1ms) SELECT COUNT(*) FROM "tasks" INNER JOIN "projects" ON "tasks"."project_id" = "projects"."id" WHERE "projects"."client_id" = $1 [["client_id", 3]] 
    User Load (5.8ms) SELECT "users".* FROM "users" WHERE "users"."id" = $1 ORDER BY "users"."id" ASC LIMIT $2 [["id", 1], ["LIMIT", 1]] 
    Task Load (100.6ms) SELECT "tasks".* FROM "tasks" INNER JOIN "projects" ON "tasks"."project_id" = "projects"."id" WHERE "projects"."client_id" = $1 ORDER BY task_end_date asc LIMIT $2 [["client_id", 3], ["LIMIT", 1]] 
    Rendering clients/index.html.erb within layouts/application 
    CACHE Project Load (0.5ms) SELECT "projects".* FROM "projects" WHERE "projects"."id" = $1 LIMIT $2 [["id", 2], ["LIMIT", 1]] 
    Rendered clients/index.html.erb within layouts/application (9.6ms) 
    CACHE Project Load (0.4ms) SELECT "projects".* FROM "projects" WHERE "projects"."id" = $1 LIMIT $2 [["id", 2], ["LIMIT", 1]] 

時のコンソールのスニペットは、ロード時間も、PRODにも耐えられません。私はクエリを洗練する前に、これは広範ではありませんでした。

すべての入力を歓迎します - 私はどのような他のコードベースを添付するのかは分かりません。

答えて

関連する問題