Skip to content

Commit

Permalink
Marketplace: Adds Product#tags
Browse files Browse the repository at this point in the history
Products can now be tagged with things like `Gluten Free` or `Vegan`,
and will show up as such under Product listings
  • Loading branch information
zspencer committed Feb 8, 2024
1 parent b6a81c7 commit 23f6ef5
Show file tree
Hide file tree
Showing 18 changed files with 157 additions and 4 deletions.
1 change: 1 addition & 0 deletions app/furniture/marketplace/bazaar.rb
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ class Marketplace
class Bazaar < ::Space
has_many :marketplaces, through: :rooms, source: :gizmos, inverse_of: :bazaar, class_name: "Marketplace"
has_many :tax_rates, inverse_of: :bazaar, dependent: :destroy
has_many :tags, inverse_of: :bazaar, dependent: :destroy

def space
becomes(Space)
Expand Down
10 changes: 10 additions & 0 deletions app/furniture/marketplace/breadcrumbs.rb
Original file line number Diff line number Diff line change
Expand Up @@ -104,6 +104,16 @@
link t("marketplace.stripe_accounts.show.link_to"), marketplace.location(child: :stripe_account)
end

crumb :marketplace_tags do |marketplace|
parent :edit_marketplace, marketplace
link(t("marketplace.tags.index.link_to"), marketplace.location(child: :tags))
end

crumb :new_marketplace_tag do |tag|
parent :marketplace_tags, tag.marketplace
link t("marketplace.tags.new.link_to"), marketplace.location(:new, child: :tag)
end

crumb :marketplace_tax_rates do |marketplace|
parent :edit_marketplace, marketplace
link t("marketplace.tax_rates.index.link_to"), marketplace.location(child: :tax_rates)
Expand Down
5 changes: 5 additions & 0 deletions app/furniture/marketplace/locales/en.yml
Original file line number Diff line number Diff line change
Expand Up @@ -136,3 +136,8 @@ en:
payment_settings:
index:
link_to: "Payment Settings"
tags:
index:
link_to: "Tags"
new:
link_to: "Add Tag"
1 change: 1 addition & 0 deletions app/furniture/marketplace/management_component.html.erb
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@
<%= render button({child: :notification_methods}, icon: :bell) if policy(marketplace.notification_methods).index? %>
<%= render button({child: :flyer}, icon: :receipt_percent) if policy(marketplace.flyer).show? %>
<%= render button({child: :vendor_representatives}, icon: :cake) if policy(marketplace.vendor_representatives).index? %>
<%= render button({child: :tags}, icon: :tag) if policy(marketplace.tags).index? %>
</nav>
<% end %>
<% end %>
Expand Down
2 changes: 2 additions & 0 deletions app/furniture/marketplace/marketplace.rb
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,8 @@ class Marketplace < Furniture
# @todo replace with through :bazaar
has_many :tax_rates, inverse_of: :marketplace

has_many :tags, through: :bazaar

has_many :products, inverse_of: :marketplace, dependent: :destroy
has_many :carts, inverse_of: :marketplace, dependent: :destroy
has_many :orders, inverse_of: :marketplace
Expand Down
3 changes: 2 additions & 1 deletion app/furniture/marketplace/policy.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ class Marketplace
class Policy < ApplicationPolicy
def create?
return true if current_person.operator?
return true if current_person.member_of?(marketplace.space)
return true if current_person.member_of?(space)

return true if shopper&.person.blank? && !current_person.authenticated?

Expand All @@ -23,6 +23,7 @@ def marketplace

object.marketplace if object.respond_to?(:marketplace)
end
delegate :space, to: :marketplace

module SpecFactories
def self.included(spec)
Expand Down
3 changes: 3 additions & 0 deletions app/furniture/marketplace/product.rb
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,9 @@ class Product < Record
has_many :ordered_products, inverse_of: :product, dependent: :destroy
has_many :orders, -> { checked_out }, through: :ordered_products, inverse_of: :products

has_many :product_tags, inverse_of: :product, dependent: :destroy
has_many :tags, through: :product_tags, inverse_of: :products

has_many :product_tax_rates, inverse_of: :product, dependent: :destroy
has_many :tax_rates, through: :product_tax_rates, inverse_of: :products

Expand Down
7 changes: 6 additions & 1 deletion app/furniture/marketplace/product/title_component.html.erb
Original file line number Diff line number Diff line change
@@ -1,2 +1,7 @@
<h3><%= name %></h3>
<p class="text-sm">Serves <%= servings %></p>
<p class="text-sm">
Serves <%= servings %>
<%- if product.tags.present? %>
(<%= product.tags.pluck(:label).join(", ") %>)
<%- end %>
</p>
2 changes: 1 addition & 1 deletion app/furniture/marketplace/product_policy.rb
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ class Marketplace
class ProductPolicy < Policy
alias_method :product, :object
def permitted_attributes(_params = nil)
%i[name description price_cents price_currency price photo restore servings] + [tax_rate_ids: []]
%i[name description price_cents price_currency price photo restore servings] + [tag_ids: [], tax_rate_ids: []]
end

def update?
Expand Down
8 changes: 8 additions & 0 deletions app/furniture/marketplace/product_tag.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
class Marketplace
class ProductTag < Record
self.table_name = :marketplace_product_tags

belongs_to :product, inverse_of: :product_tags
belongs_to :tag, inverse_of: :product_tags
end
end
2 changes: 2 additions & 0 deletions app/furniture/marketplace/products/_form.html.erb
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,8 @@
<%= render "number_field", { attribute: :servings, form: f, min: 0, step: 1} %>
<%= render "money_field", { attribute: :price, form: f, min: 0, step: 0.01} %>
<%= render "collection_check_boxes", { attribute: :tag_ids, collection: bazaar.tags, value_method: :id,
text_method: :label, form: f} %>
<%= render "collection_check_boxes", { attribute: :tax_rate_ids, collection: bazaar.tax_rates, value_method: :id, text_method: :label, form: f} %>
<%- if product.photo.present? %>
<div>
Expand Down
1 change: 1 addition & 0 deletions app/furniture/marketplace/routes.rb
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ def self.append_routes(router)
router.resources :products
router.resource :stripe_account, only: [:show, :new, :create]
router.resources :stripe_events
router.resources :tags
router.resources :tax_rates
router.resources :vendor_representatives
router.resources :payment_settings, only: [:index]
Expand Down
12 changes: 12 additions & 0 deletions app/furniture/marketplace/tag.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
class Marketplace
class Tag < Record
self.table_name = "marketplace_tags"

belongs_to :bazaar, inverse_of: :tags
has_many :product_tags, inverse_of: :tag, dependent: :destroy
has_many :products, through: :product_tags, inverse_of: :tags

attr_accessor :marketplace
location(parent: :marketplace)
end
end
32 changes: 32 additions & 0 deletions app/furniture/marketplace/tag_policy.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
# frozen_string_literal: true

class Marketplace
class TagPolicy < Policy
alias_method :tag, :object
def space
tag.bazaar
end

def permitted_attributes(_params = nil)
%i[label]
end

def update?
return false unless current_person.authenticated?

super
end

alias_method :create?, :update?

def show?
true
end

class Scope < ApplicationScope
def resolve
scope.all
end
end
end
end
31 changes: 31 additions & 0 deletions app/furniture/marketplace/tags_controller.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
# frozen_string_literal: true

class Marketplace
class TagsController < Controller
# Apparently, `tag` is used inside of `turbo_frame_tag`, so if we define a
# helper_method named `tag` our method gets called when it really shouldn't
# be... so `mtag` it is. For now.
expose :mtag, scope: -> { tags }, model: Tag
expose :tags, -> { policy_scope(bazaar.tags.create_with(marketplace: marketplace)) }

def new
authorize(mtag)
end

def create
if authorize(mtag).save
redirect_to marketplace.location(child: :tags)
else
render :new
end
end

def index
skip_authorization
end

def mtag_params
policy(Tag).permit(params.require(:tag))
end
end
end
17 changes: 17 additions & 0 deletions db/migrate/20240208025354_create_marketplace_product_tags.rb
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
class CreateMarketplaceProductTags < ActiveRecord::Migration[7.1]
def change
create_table :marketplace_tags, id: :uuid do |t|
t.references :bazaar, type: :uuid
t.string :label

t.timestamps
end

create_table :marketplace_product_tags, id: :uuid do |t|
t.references :product, type: :uuid, foreign_key: {to_table: :marketplace_products}
t.references :tag, type: :uuid, foreign_key: {to_table: :marketplace_tags}

t.timestamps
end
end
end
21 changes: 20 additions & 1 deletion db/schema.rb
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@
#
# It's strongly recommended that you check this file into your version control system.

ActiveRecord::Schema[7.1].define(version: 2024_02_07_040004) do
ActiveRecord::Schema[7.1].define(version: 2024_02_08_025354) do
# These are extensions that must be enabled in order to support this database
enable_extension "pgcrypto"
enable_extension "plpgsql"
Expand Down Expand Up @@ -192,6 +192,15 @@
t.index ["shopper_id"], name: "index_marketplace_orders_on_shopper_id"
end

create_table "marketplace_product_tags", id: :uuid, default: -> { "gen_random_uuid()" }, force: :cascade do |t|
t.uuid "product_id"
t.uuid "tag_id"
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
t.index ["product_id"], name: "index_marketplace_product_tags_on_product_id"
t.index ["tag_id"], name: "index_marketplace_product_tags_on_tag_id"
end

create_table "marketplace_product_tax_rates", id: :uuid, default: -> { "gen_random_uuid()" }, force: :cascade do |t|
t.uuid "tax_rate_id"
t.uuid "product_id"
Expand Down Expand Up @@ -222,6 +231,14 @@
t.index ["person_id"], name: "index_marketplace_shoppers_on_person_id", unique: true
end

create_table "marketplace_tags", id: :uuid, default: -> { "gen_random_uuid()" }, force: :cascade do |t|
t.uuid "bazaar_id"
t.string "label"
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
t.index ["bazaar_id"], name: "index_marketplace_tags_on_bazaar_id"
end

create_table "marketplace_tax_rates", id: :uuid, default: -> { "gen_random_uuid()" }, force: :cascade do |t|
t.float "tax_rate"
t.string "label"
Expand Down Expand Up @@ -328,6 +345,8 @@
add_foreign_key "marketplace_notification_methods", "furnitures", column: "marketplace_id"
add_foreign_key "marketplace_orders", "marketplace_delivery_areas", column: "delivery_area_id"
add_foreign_key "marketplace_orders", "marketplace_shoppers", column: "shopper_id"
add_foreign_key "marketplace_product_tags", "marketplace_products", column: "product_id"
add_foreign_key "marketplace_product_tags", "marketplace_tags", column: "tag_id"
add_foreign_key "marketplace_product_tax_rates", "marketplace_products", column: "product_id"
add_foreign_key "marketplace_product_tax_rates", "marketplace_tax_rates", column: "tax_rate_id"
add_foreign_key "marketplace_products", "furnitures", column: "marketplace_id"
Expand Down
3 changes: 3 additions & 0 deletions spec/furniture/marketplace/product_tags_system_spec.rb
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,9 @@
click_link("⚙️ Edit")
end

check("🚫🌾 Gluten Free")
click_button("Save")

visit(marketplace)

within(muffins) do
Expand Down

0 comments on commit 23f6ef5

Please sign in to comment.