2016-07-22 11 views
3

In dieser App rails habe ich eine Methode, die von einem Controller aufgerufen wird, der eine aktive Datensatzbeziehung von Sites und ein Array von Filtern verwendet. Die Methode gibt alle Sites in der Relation zurück alle Filter im Array. Hier ist die Methode:Den Schnittpunkt zweier aktiver Datensatzrelationen erhalten, rails

def filter_sites(sites, filters) 

    if filters.count > 0 
    filterable = sites.tag_join 
    filters.each { |f| sites = sites & filterable.with_tag(f) } 
    end 

    return sites 
end 

Hier sind die Rahmen, die verwendet werden:

def self.tag_join 
    joins(:tags).distinct 
end 

def self.with_tag(tag_id) 
    where('sites_tags.tag_id = ?',tag_id) 
end 

Dies korrekt funktioniert, aber das Problem ist, dass es ein Array zurückgibt. Meine Frage ist; Gibt es einen effektiveren Weg oder schreiben Sie diese Methode und geben Sie eine aktive Datensatzbeziehung zurück? Wie später im Code müssen weitere Abfragen verkettet werden.

Jede Hilfe sehr geschätzt.

+0

Sehen Sie sich die oder Methode aus dem aktiven Datensatz an –

+1

Eine Möglichkeit, dies zu tun - aber was hässlich ist - ist die Verwendung von SQL 'INTERSECT'. Sie konstruieren grundsätzlich eine ansonsten identische Abfrage für jedes Tag und dann "INTERSECT" sie. Das ist schrecklich, weil Sie es manuell tun müssen, aber es funktioniert und gibt ein ActiveRecord-Objekt zurück, das Sie verketten können. Ich muss auch fragen: Kannst du 'sites.where ('sites_tags.tag_id =?', Filtert [0]). Where ('sites_tags.tag_id =?', Filtert [1]). Where (.. .) '? – henrebotha

+0

Ist das nicht genauso hässlich? Es ist ein Array variabler Länge von Tags, so dass dies mit einer Schleife geschrieben werden müsste. Ich hätte gedacht, dass sie eine Art und Weise, dies zu tun, ihre allgemeine Funktionalität ... – PhilBrockwell

Antwort

1

Sie könnten eine merge tun. Ein wird zurückgegeben, aber es ist ein sauberer Anruf, bequem und einfach zu warten.

Verwandte Themen