これは別のアプローチです。
Offer.find_by_sql("SELECT * FROM offers o WHERE NOT EXISTS (SELECT * FROM products WHERE products.offer_id = o.id AND service_id IS NULL)")
ORMの考え方でさえ、SQLを抽象化するというものですが、この種の複雑なクエリでは、クエリをさらに複雑にせずに、最も単純なソリューションを選択する方がよいと思います。
これは別のアプローチです。
Offer.find_by_sql("SELECT * FROM offers o WHERE NOT EXISTS (SELECT * FROM products WHERE products.offer_id = o.id AND service_id IS NULL)")
ORMの考え方でさえ、SQLを抽象化するというものですが、この種の複雑なクエリでは、クエリをさらに複雑にせずに、最も単純なソリューションを選択する方がよいと思います。