Skip to content

Commit

Permalink
Org profile theme (#341)
Browse files Browse the repository at this point in the history
* Add instance variables that will be used in the dashboard view

* Add template html and begin inital formatting to utilize instance variables scoped to organization

* Add components needed to utilize geeksui theme. Added avatar section- not yet functional

* Play around with understanding avatarable, and look at orf_profiles edit view

* standardrb

* Add delegate to org_profile model to gain access to name attribute

* Edit header to look more like Geeks UI theme, and add current org name

* Edit card to have two columns as requested, comment code to make it clear and readable

* Standardrb

* Begin testing for organization profile edit

* add translation

* Add delegation back in

* Tinker with views to see if nested attributes will start updating

* Continue working on test to ensure full functionality on profile update

* Create happy path testing for organization_profile edit page

* Remove html formatting in update action, update profile params

* Add and remove pry multiple times

* Add delgate so we have access to organization name in the edit action

* Remove name field and add in about us

* Standard rb

* Remove bang from update so flash messages appear correctly

* Add email validation so users cannot enter an invalid email

* Add sad path testing to ensure full functionality

* Standard rb

* Add tests for new and previous validations

* Add Organization Details header and move avatar section out of card body

* Add horizontal rule

* Add condition to set organization, and remove set organization from org profil test suit

* standardrb
  • Loading branch information
jadekstewart3 authored Nov 29, 2023
1 parent 259ffd7 commit fe6a61a
Show file tree
Hide file tree
Showing 9 changed files with 218 additions and 58 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -7,13 +7,10 @@ def edit

def update
@organization_profile = Current.organization.profile

respond_to do |format|
if @organization_profile.update(organization_profile_params)
format.html { redirect_to dashboard_index_path, notice: "Profile updated" }
else
format.html { render :edit, status: :unprocessable_entity }
end
if @organization_profile.update(organization_profile_params)
redirect_to dashboard_index_path, notice: "Your profile has been updated!"
else
render :edit, status: :unprocessable_entity
end
end

Expand All @@ -23,7 +20,8 @@ def organization_profile_params
params.require(:organization_profile).permit(
:phone_number,
:email,
location_attributes: %i[city_town country province_state id]
:about_us,
location_attributes: %i[city_town country province_state]
)
end
end
4 changes: 3 additions & 1 deletion app/models/organization_profile.rb
Original file line number Diff line number Diff line change
Expand Up @@ -24,13 +24,15 @@
class OrganizationProfile < ApplicationRecord
belongs_to :location
belongs_to :organization, inverse_of: :profile

accepts_nested_attributes_for :location
validates_associated :location

before_save :normalize_phone

validates :phone_number, phone: {possible: true, allow_blank: true}
validates_format_of :email, with: /\A([^@\s]+)@((?:[-a-z0-9]+\.)+[a-z]{2,})\z/i

delegate :name, to: :organization

private

Expand Down
131 changes: 85 additions & 46 deletions app/views/organizations/organization_profiles/_form.html.erb
Original file line number Diff line number Diff line change
Expand Up @@ -4,57 +4,96 @@
<%= t '.please_fix_the_errors' %>
</div>
<% end %>
<hr class="my-5">
<!-- Avatar section- not yet functional -->
<div class="d-lg-flex align-items-center justify-content-between">
<div class="d-flex align-items-center mb-4 mb-lg-0">
<!-- Avatar Image -->
<img src="../assets/images/avatar/avatar-3.jpg" id="img-uploaded" class="avatar-xl rounded-circle" alt="avatar">

<!--Administrative details section-->
<div class='card p-5 mb-5'>
<h3>Contact</h3>
<!-- Avatar Details -->
<div class="ms-3">
<h4 class="mb-0">Your avatar</h4>
<p class="mb-0">PNG or JPG, size must be between 10kb and 1Mb</p>
</div>
</div>

<div class="form-group">
<%= form.telephone_field :phone_number,
autofocus: true,
placeholder: "10 digit number",
class: 'form-control' %>
<div>
<a href="#" class="btn btn-outline-secondary btn-sm">Update</a>
<a href="#" class="btn btn-outline-danger btn-sm">Delete</a>
</div>
</div>

<div class="form-group">
<%= form.text_field :email, placeholder: "[email protected]", class: 'form-control' %>
<hr class="my-5">
<div class='card-body'>
<div class="d-lg-flex align-items-center justify-content-between">
<h3 class="mb-1">Organization Details<h3>
<p class="text-muted mb-3" style="font-size: 12px;">Edit your organization's information.<p>
</div>

<%# nested form for locations table %>
<div class="form-group bigger" data-controller="country-state">
<%= form.fields_for :location do |location| %>
<%= location.select :country,
CS.countries.invert,
{ prompt: "Please select" },
'data-path': country_states_path(:country),
'data-country-state-target': 'country',
'data-action': 'change->country-state#updateStates',
'data-initial-value': location.object.country,
required: true,
class: 'form-control' %>
<% profile.location.custom_messages(:country).each do |error| %>
<div class="alert alert-danger mt-1" role="alert"><%= error.message %></div>
<% end %>
<!-- Administrative details section -->
<div class="row mt-3">
<!-- First Column -->
<div class="col-lg-6">
<%= form.fields_for :organization do |org_form| %>
<form class="mb-3">
<!-- Phone Number -->
<div class="form-group">
<%= form.telephone_field :phone_number,
autofocus: true,
placeholder: "10 digit number",
class: 'form-control' %>
</div>

<%= location.select :province_state,
CS.states(location.object.country).invert,
{ prompt: "Please select" },
'data-country-state-target': 'state',
required: true,
class: 'form-control' %>
<% profile.location.custom_messages(:province_state).each do |error| %>
<div class="alert alert-danger mt-1" role="alert"><%= error.message %></div>
<% end %>
<!-- Email -->
<div class="form-group">
<%= form.text_field :email, placeholder: "[email protected]", class: 'form-control' %>
</div>

<!-- About Us -->
<div class="form-group">
<%= form.text_field :about_us, placeholder: "We get pets into loving homes!", class: 'form-control' %>
</div>
</form>
<% end %>
</div>

<!-- Second Column -->
<div class="col-lg-6">

<!-- Nested Form for Locations Table -->
<div class="form-group bigger" data-controller="country-state">
<%= form.fields_for :location do |location| %>
<!-- Country Select -->
<%= location.select :country,
CS.countries.invert,
{ prompt: "Please select" },
'data-path': country_states_path(:country),
'data-country-state-target': 'country',
'data-action': 'change->country-state#updateStates',
'data-initial-value': location.object.country,
required: true,
class: 'form-control' %>

<!-- Province/State Select -->
<%= location.select :province_state,
CS.states(location.object.country).invert,
{ prompt: "Please select" },
'data-country-state-target': 'state',
required: true,
class: 'form-control' %>

<%= location.text_field :city_town, class: 'form-control' %>
<% profile.location.custom_messages(:city_town).each do |error| %>
<div class="alert alert-danger mt-1" role="alert"><%= error.message %></div>
<!-- City/Town Text Field -->
<%= location.text_field :city_town, class: 'form-control' %>
<% end %>
<% end %>
</div>
</div> <!--card-->

<div>
<%= form.submit 'Save profile', class: 'btn btn-outline-dark mb-3' %>
</div>
<% end %>
</div>
</div>
</div>

<div class="row mt-3">
<div class="col-lg-12">
<%= form.submit 'Save profile', class: 'btn btn-primary' %>
</div>
</div>
</div> <!-- End of Card Body -->
<% end %>

8 changes: 6 additions & 2 deletions app/views/organizations/organization_profiles/edit.html.erb
Original file line number Diff line number Diff line change
Expand Up @@ -3,8 +3,11 @@
<div class="container">
<div class="text-center">
<h1 class="section-heading text-uppercase underline">
<%= t('.edit_profile') %>
<%= @organization_profile.name %> <%= t('.profile_details') %>
</h1>
<p class="mb-0">
<%= t('.manage_your_own_account_settings') %>
</p>
</div>
</div> <!--container-->
</header>
Expand All @@ -17,4 +20,5 @@
<%= link_to t('general.back'), dashboard_index_path %>
</div>
</div> <!--container-->
</section>
</section>

1 change: 1 addition & 0 deletions config/locales/en.yml
Original file line number Diff line number Diff line change
Expand Up @@ -153,6 +153,7 @@ en:
organization_profiles:
form:
please_fix_the_errors: "Please fix the errors highlighted below."
manage_your_own_account_settings: "You have full control to manage your own account settings."
edit:
edit_profile: "Edit Profile"
adopter_applications:
Expand Down
3 changes: 3 additions & 0 deletions test/controllers/root_controller_test.rb
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@
require "test_helper"

class RootsControllerTest < ActionDispatch::IntegrationTest
setup do
set_organization(nil)
end
context "GET #index" do
should "get the root url" do
get root_url
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,99 @@
# frozen_string_literal: true

require "test_helper"

class OrganizationProfile::EditProfileTest < ActionDispatch::IntegrationTest
setup do
@org = ActsAsTenant.test_tenant
@org_profile = @org.profile
admin = create(:user, :staff_admin, organization: @org)
sign_in admin
get edit_organization_profile_path(@org_profile)
end

test "all expected fields are present on the edit organization profile page" do
assert_select "h4", text: "Your avatar"
assert_select "p", text: "PNG or JPG, size must be between 10kb and 1Mb"

assert_select "label", text: "Phone number"
assert_select "input[name='organization_profile[phone_number]'][type='tel']"

assert_select "label", text: "Email"
assert_select "input[name='organization_profile[email]'][type='text']"

assert_select "label", text: "Country"
assert_select "select[name='organization_profile[location_attributes][province_state]']"

assert_select "label", text: "City/Town"
assert_select "input[name='organization_profile[location_attributes][city_town]'][type='text']"

assert_select 'input[type="submit"][value="Save profile"]'
end

test "organization profile updates with the submission of the form" do
puts "!!!!!!!!#{@org_profile.id}"
patch organization_profile_path(@org_profile), params: {
organization_profile: {
email: "[email protected]",
phone_number: "3038947563",
about_us: "Finding pets loving homes across the front range!",
location_attributes: {
country: "United States",
province_state: "Colorado",
city_town: "Golden"
}
}
}
@org_profile.reload

assert_response :redirect
follow_redirect!
assert_response :success

assert_equal "[email protected]", @org_profile.email
assert_equal "+13038947563", @org_profile.phone_number
assert_equal "Finding pets loving homes across the front range!", @org_profile.about_us
assert_equal "United States", @org_profile.location.country
assert_equal "Colorado", @org_profile.location.province_state
assert_equal "Golden", @org_profile.location.city_town
end

test "organization profile updates with only some form fields to update" do
patch organization_profile_path(@org_profile), params: {
organization_profile: {
phone_number: "3038947542",
about_us: "Finding pets loving homes across the Denver Metro area"
}
}
@org_profile.reload

assert_response :redirect
follow_redirect!
assert_response :success

assert_equal "+13038947542", @org_profile.phone_number
assert_equal "Finding pets loving homes across the Denver Metro area", @org_profile.about_us
end

test "organization profile does not update with a non valid phone number" do
patch organization_profile_path(@org_profile), params: {
organization_profile: {
phone_number: "303894754232849320"
}
}
@org_profile.reload
assert_response :unprocessable_entity
assert_select "div.alert.alert-danger.mt-1", text: "Please fix the errors highlighted below."
end

test "organization profile does not update with an invalid email" do
patch organization_profile_path(@org_profile), params: {
organization_profile: {
email: "happy_pets_bad_email.com"
}
}
@org_profile.reload
assert_response :unprocessable_entity
assert_select "div.alert.alert-danger.mt-1", text: "Please fix the errors highlighted below."
end
end
9 changes: 9 additions & 0 deletions test/models/organization_profile_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,15 @@ class OrganizationProfileTest < ActiveSupport::TestCase
should accept_nested_attributes_for(:location)
end

context "validations" do
should allow_value("123-456-7890").for(:phone_number)
should allow_value("").for(:phone_number)
should_not allow_value("invalid_number").for(:phone_number)

should allow_value("[email protected]").for(:email)
should_not allow_value("invalid_email.com").for(:email)
end

context "callbacks" do
subject { build(:organization_profile) }

Expand Down
7 changes: 6 additions & 1 deletion test/test_helper.rb
Original file line number Diff line number Diff line change
Expand Up @@ -23,11 +23,16 @@ class ActiveSupport::TestCase
include Devise::Test::IntegrationHelpers

def set_organization(organization)
Rails.application.routes.default_url_options[:script_name] = "/#{organization.slug}"
Rails.application.routes.default_url_options[:script_name] = if organization
"/#{organization.slug}"
else
""
end
end

setup do
ActsAsTenant.test_tenant = create(:organization, slug: "test")
set_organization(ActsAsTenant.test_tenant)
end

def teardown
Expand Down

0 comments on commit fe6a61a

Please sign in to comment.