Merge branch 'staging'
This commit is contained in:
3
Gemfile
3
Gemfile
@ -16,10 +16,11 @@ gem 'html2haml'
|
|||||||
gem 'devise'
|
gem 'devise'
|
||||||
gem 'carrierwave', '>= 3.0.0.beta', '< 4.0'
|
gem 'carrierwave', '>= 3.0.0.beta', '< 4.0'
|
||||||
|
|
||||||
|
gem 'kaminari'
|
||||||
gem "ruby2js" , git: "https://github.com/ruby2js/ruby2js/" , branch: "haml_fix"
|
gem "ruby2js" , git: "https://github.com/ruby2js/ruby2js/" , branch: "haml_fix"
|
||||||
gem 'thredded', '~> 1.0'
|
gem 'thredded', '~> 1.0'
|
||||||
gem "rest-client"
|
gem "rest-client"
|
||||||
|
gem "pundit"
|
||||||
|
|
||||||
gem "simple_form" , "5.1.0"
|
gem "simple_form" , "5.1.0"
|
||||||
gem "simple_form_tailwind_css"
|
gem "simple_form_tailwind_css"
|
||||||
|
@ -439,10 +439,12 @@ DEPENDENCIES
|
|||||||
haml-rails
|
haml-rails
|
||||||
html2haml
|
html2haml
|
||||||
importmap-rails
|
importmap-rails
|
||||||
|
kaminari
|
||||||
merged!
|
merged!
|
||||||
mina
|
mina
|
||||||
passenger
|
passenger
|
||||||
pg (~> 1.1)
|
pg (~> 1.1)
|
||||||
|
pundit
|
||||||
rails (~> 7.0)
|
rails (~> 7.0)
|
||||||
rest-client
|
rest-client
|
||||||
ruby2js!
|
ruby2js!
|
||||||
|
BIN
app/assets/images/no_image.png
Normal file
BIN
app/assets/images/no_image.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 23 KiB |
@ -1,9 +1,13 @@
|
|||||||
class ApplicationController < ActionController::Base
|
class ApplicationController < ActionController::Base
|
||||||
before_action :configure_permitted_parameters, if: :devise_controller?
|
|
||||||
|
include Pundit::Authorization
|
||||||
|
alias :current_user :current_member #for pundit
|
||||||
|
rescue_from Pundit::NotAuthorizedError, with: :user_not_authorized
|
||||||
|
|
||||||
protected
|
protected
|
||||||
|
|
||||||
def configure_permitted_parameters
|
def user_not_authorized
|
||||||
devise_parameter_sanitizer.permit(:sign_up, keys: [:name])
|
flash[:alert] = "You are not authorized to perform this action."
|
||||||
|
redirect_back(fallback_location: root_path)
|
||||||
end
|
end
|
||||||
end
|
end
|
||||||
|
65
app/controllers/events_controller.rb
Normal file
65
app/controllers/events_controller.rb
Normal file
@ -0,0 +1,65 @@
|
|||||||
|
class EventsController < ApplicationController
|
||||||
|
before_action :set_event, only: %i[ show edit update destroy ]
|
||||||
|
|
||||||
|
# GET /events
|
||||||
|
def index
|
||||||
|
@events = Event.all
|
||||||
|
end
|
||||||
|
|
||||||
|
# GET /events/1
|
||||||
|
def show
|
||||||
|
end
|
||||||
|
|
||||||
|
# GET /events/new
|
||||||
|
def new
|
||||||
|
kind = params[:profile]
|
||||||
|
kind = Profile.types.first unless Profile.types.include?(kind)
|
||||||
|
profile = current_member.profile(kind)
|
||||||
|
if(profile)
|
||||||
|
@event = Event.new profile: profile
|
||||||
|
else
|
||||||
|
redirect_to member_path(current_member), notice: "No such profile #{kind}."
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
# GET /events/1/edit
|
||||||
|
def edit
|
||||||
|
end
|
||||||
|
|
||||||
|
# POST /events
|
||||||
|
def create
|
||||||
|
@event = Event.new(event_params)
|
||||||
|
|
||||||
|
if @event.save
|
||||||
|
redirect_to @event, notice: "Event was successfully created."
|
||||||
|
else
|
||||||
|
render :new, status: :unprocessable_entity
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
# PATCH/PUT /events/1
|
||||||
|
def update
|
||||||
|
if @event.update(event_params)
|
||||||
|
redirect_to @event, notice: "Event was successfully updated."
|
||||||
|
else
|
||||||
|
render :edit, status: :unprocessable_entity
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
# DELETE /events/1
|
||||||
|
def destroy
|
||||||
|
@event.destroy
|
||||||
|
redirect_to events_url, notice: "Event was successfully destroyed."
|
||||||
|
end
|
||||||
|
|
||||||
|
private
|
||||||
|
# Use callbacks to share common setup or constraints between actions.
|
||||||
|
def set_event
|
||||||
|
@event = Event.find(params[:id])
|
||||||
|
end
|
||||||
|
|
||||||
|
# Only allow a list of trusted parameters through.
|
||||||
|
def event_params
|
||||||
|
params.require(:event).permit(:name, :text, :start_date, :end_date, :profile_id, :picture)
|
||||||
|
end
|
||||||
|
end
|
@ -3,7 +3,7 @@ class MembersController < ApplicationController
|
|||||||
|
|
||||||
# GET /members
|
# GET /members
|
||||||
def index
|
def index
|
||||||
@members = Member.all
|
@members = Member.page params[:page]
|
||||||
end
|
end
|
||||||
|
|
||||||
# GET /members/1
|
# GET /members/1
|
||||||
|
64
app/controllers/profiles_controller.rb
Normal file
64
app/controllers/profiles_controller.rb
Normal file
@ -0,0 +1,64 @@
|
|||||||
|
class ProfilesController < ApplicationController
|
||||||
|
before_action :set_profile, only: %i[ show edit update destroy ]
|
||||||
|
|
||||||
|
# GET /profiles
|
||||||
|
def index
|
||||||
|
@profiles = Profile.page params[:page]
|
||||||
|
end
|
||||||
|
|
||||||
|
# GET /profiles/1
|
||||||
|
def show
|
||||||
|
end
|
||||||
|
|
||||||
|
# GET /profiles/new
|
||||||
|
def new
|
||||||
|
kind = params[:kind]
|
||||||
|
kind = Profile.types.first unless Profile.types.include?(kind)
|
||||||
|
@profile = Profile.new kind: kind
|
||||||
|
end
|
||||||
|
|
||||||
|
# GET /profiles/1/edit
|
||||||
|
def edit
|
||||||
|
authorize @profile
|
||||||
|
end
|
||||||
|
|
||||||
|
# POST /profiles
|
||||||
|
def create
|
||||||
|
@profile = Profile.new(profile_params)
|
||||||
|
@profile.member = current_member
|
||||||
|
|
||||||
|
if @profile.save
|
||||||
|
redirect_to member_path(current_member), notice: "Successfully created #{@profile.Kind} profile"
|
||||||
|
else
|
||||||
|
render :new, status: :unprocessable_entity
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
# PATCH/PUT /profiles/1
|
||||||
|
def update
|
||||||
|
authorize @profile
|
||||||
|
if @profile.update(profile_params)
|
||||||
|
redirect_to member_path(current_member), notice: "#{@profile.Kind} profile was updated."
|
||||||
|
else
|
||||||
|
render :edit, status: :unprocessable_entity
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
# DELETE /profiles/1
|
||||||
|
def destroy
|
||||||
|
authorize @profile
|
||||||
|
@profile.destroy
|
||||||
|
redirect_to member_path(current_member), notice: "#{@profile.Kind} profile was successfully destroyed."
|
||||||
|
end
|
||||||
|
|
||||||
|
private
|
||||||
|
# Use callbacks to share common setup or constraints between actions.
|
||||||
|
def set_profile
|
||||||
|
@profile = Profile.find(params[:id])
|
||||||
|
end
|
||||||
|
|
||||||
|
# Only allow a list of trusted parameters through.
|
||||||
|
def profile_params
|
||||||
|
params.require(:profile).permit(:name, :bio, :picture, :kind)
|
||||||
|
end
|
||||||
|
end
|
@ -1,21 +1,12 @@
|
|||||||
require "redcarpet"
|
|
||||||
|
|
||||||
module ApplicationHelper
|
module ApplicationHelper
|
||||||
|
include Merged::SharedHelper
|
||||||
|
|
||||||
def renderer
|
def shorten(text , to = 100)
|
||||||
options = {hard_wrap: true , autolink: true, no_intra_emphasis: true ,
|
return "" if text.blank?
|
||||||
safe_links_only: true, no_styles: true ,
|
"#{text[0..to]} . . . ".html_safe
|
||||||
link_attributes: { target: '_blank' }}
|
|
||||||
html = Redcarpet::Render::HTML.new(options)
|
|
||||||
Redcarpet::Markdown.new(html, options)
|
|
||||||
end
|
end
|
||||||
|
|
||||||
def markdown(text)
|
|
||||||
return "" if text.blank?
|
|
||||||
text = text.text unless text.is_a?(String)
|
|
||||||
return "" if text.blank?
|
|
||||||
self.renderer.render(text).html_safe
|
|
||||||
end
|
|
||||||
|
|
||||||
def main_app
|
def main_app
|
||||||
Rails.application.routes.url_helpers
|
Rails.application.routes.url_helpers
|
||||||
@ -25,4 +16,13 @@ module ApplicationHelper
|
|||||||
"mr-3 inline-block rounded-lg px-3 py-2 text-md font-medium border border-gray-500"
|
"mr-3 inline-block rounded-lg px-3 py-2 text-md font-medium border border-gray-500"
|
||||||
end
|
end
|
||||||
|
|
||||||
|
def image_for(someone , classes = "")
|
||||||
|
if someone.picture.blank?
|
||||||
|
image = asset_url("no_image.png")
|
||||||
|
else
|
||||||
|
image = someone.picture.url
|
||||||
|
end
|
||||||
|
image_tag(image , alt: someone.name , class: classes )
|
||||||
|
end
|
||||||
|
|
||||||
end
|
end
|
||||||
|
2
app/helpers/events_helper.rb
Normal file
2
app/helpers/events_helper.rb
Normal file
@ -0,0 +1,2 @@
|
|||||||
|
module EventsHelper
|
||||||
|
end
|
2
app/helpers/profiles_helper.rb
Normal file
2
app/helpers/profiles_helper.rb
Normal file
@ -0,0 +1,2 @@
|
|||||||
|
module ProfilesHelper
|
||||||
|
end
|
@ -20,8 +20,8 @@ class Entity < ApplicationRecord
|
|||||||
end
|
end
|
||||||
|
|
||||||
def self.response(path = "")
|
def self.response(path = "")
|
||||||
host = Rails.credentials.weather_dev
|
host = Rails.application.credentials.weather_dev
|
||||||
host = Rails.credentials.weather_pro if Rails.env.production?
|
host = Rails.application.credentials.weather_pro if Rails.env.production?
|
||||||
token = Rails.application.credentials.weather_token
|
token = Rails.application.credentials.weather_token
|
||||||
begin
|
begin
|
||||||
all = RestClient.get( "#{host}:8123/api/states#{path}" ,
|
all = RestClient.get( "#{host}:8123/api/states#{path}" ,
|
||||||
|
11
app/models/event.rb
Normal file
11
app/models/event.rb
Normal file
@ -0,0 +1,11 @@
|
|||||||
|
class Event < ApplicationRecord
|
||||||
|
belongs_to :profile
|
||||||
|
|
||||||
|
validates :name , presence: true
|
||||||
|
validates :text , presence: true
|
||||||
|
validates :start_date , presence: true
|
||||||
|
validates :picture , presence: true
|
||||||
|
|
||||||
|
mount_uploader :picture, PictureUploader
|
||||||
|
|
||||||
|
end
|
@ -7,11 +7,19 @@ class Member < ApplicationRecord
|
|||||||
mount_uploader :picture, PictureUploader
|
mount_uploader :picture, PictureUploader
|
||||||
|
|
||||||
has_many :entities
|
has_many :entities
|
||||||
|
has_many :profiles
|
||||||
|
|
||||||
def admin
|
Profile.types.each do |kind|
|
||||||
true
|
define_method :kind do
|
||||||
|
Profile.where( member_id: self.id).where(kind: kind).first
|
||||||
end
|
end
|
||||||
|
end
|
||||||
|
def profile( kind )
|
||||||
|
Profile.where( member_id: self.id).where(kind: kind).first
|
||||||
|
end
|
||||||
|
|
||||||
def admin?
|
def admin?
|
||||||
true
|
email == "torsten@villataika.fi"
|
||||||
end
|
end
|
||||||
|
alias :admin :admin?
|
||||||
end
|
end
|
||||||
|
19
app/models/profile.rb
Normal file
19
app/models/profile.rb
Normal file
@ -0,0 +1,19 @@
|
|||||||
|
class Profile < ApplicationRecord
|
||||||
|
belongs_to :member
|
||||||
|
has_many :events
|
||||||
|
|
||||||
|
validates :name , presence: true
|
||||||
|
validates :kind , presence: true
|
||||||
|
validates :bio , presence: true
|
||||||
|
validates :picture , presence: true
|
||||||
|
|
||||||
|
mount_uploader :picture, PictureUploader
|
||||||
|
|
||||||
|
def self.types
|
||||||
|
["member" , "artist" , "teacher"]
|
||||||
|
end
|
||||||
|
|
||||||
|
def Kind
|
||||||
|
self.kind.capitalize
|
||||||
|
end
|
||||||
|
end
|
53
app/policies/application_policy.rb
Normal file
53
app/policies/application_policy.rb
Normal file
@ -0,0 +1,53 @@
|
|||||||
|
# frozen_string_literal: true
|
||||||
|
|
||||||
|
class ApplicationPolicy
|
||||||
|
attr_reader :member, :record
|
||||||
|
|
||||||
|
def initialize(member, record)
|
||||||
|
@member = member
|
||||||
|
@record = record
|
||||||
|
end
|
||||||
|
|
||||||
|
def index?
|
||||||
|
false
|
||||||
|
end
|
||||||
|
|
||||||
|
def show?
|
||||||
|
false
|
||||||
|
end
|
||||||
|
|
||||||
|
def create?
|
||||||
|
false
|
||||||
|
end
|
||||||
|
|
||||||
|
def new?
|
||||||
|
create?
|
||||||
|
end
|
||||||
|
|
||||||
|
def update?
|
||||||
|
false
|
||||||
|
end
|
||||||
|
|
||||||
|
def edit?
|
||||||
|
update?
|
||||||
|
end
|
||||||
|
|
||||||
|
def destroy?
|
||||||
|
false
|
||||||
|
end
|
||||||
|
|
||||||
|
class Scope
|
||||||
|
def initialize(member, scope)
|
||||||
|
@member = member
|
||||||
|
@scope = scope
|
||||||
|
end
|
||||||
|
|
||||||
|
def resolve
|
||||||
|
raise NotImplementedError, "You must define #resolve in #{self.class}"
|
||||||
|
end
|
||||||
|
|
||||||
|
private
|
||||||
|
|
||||||
|
attr_reader :member, :scope
|
||||||
|
end
|
||||||
|
end
|
14
app/policies/edit_own_policy.rb
Normal file
14
app/policies/edit_own_policy.rb
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
# allows to edit/detroy own data
|
||||||
|
# which can be viewed by anyone
|
||||||
|
class EditOwnPolicy < ApplicationPolicy
|
||||||
|
def edit?
|
||||||
|
return true member.admin?
|
||||||
|
owner?
|
||||||
|
end
|
||||||
|
def owner?
|
||||||
|
member == record.member
|
||||||
|
end
|
||||||
|
alias :update? :edit?
|
||||||
|
alias :destroy? :edit?
|
||||||
|
|
||||||
|
end
|
14
app/policies/entity_policy.rb
Normal file
14
app/policies/entity_policy.rb
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
class EntityPolicy < ApplicationPolicy
|
||||||
|
|
||||||
|
def owner?
|
||||||
|
member.admin?
|
||||||
|
end
|
||||||
|
alias :owner? :index?
|
||||||
|
alias :owner? :show?
|
||||||
|
alias :owner? :create?
|
||||||
|
alias :owner? :new?
|
||||||
|
alias :owner? :update?
|
||||||
|
alias :owner? :edit?
|
||||||
|
alias :owner? :destroy?
|
||||||
|
|
||||||
|
end
|
13
app/policies/event_policy.rb
Normal file
13
app/policies/event_policy.rb
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
class EventPolicy < EditOwnPolicy
|
||||||
|
|
||||||
|
def owner?
|
||||||
|
member == record.profile.member
|
||||||
|
end
|
||||||
|
|
||||||
|
class Scope < Scope
|
||||||
|
# NOTE: Be explicit about which records you allow access to!
|
||||||
|
# def resolve
|
||||||
|
# scope.all
|
||||||
|
# end
|
||||||
|
end
|
||||||
|
end
|
6
app/policies/member_policy.rb
Normal file
6
app/policies/member_policy.rb
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
class MemberPolicy < EditOwnPolicy
|
||||||
|
|
||||||
|
|
||||||
|
class Scope < Scope
|
||||||
|
end
|
||||||
|
end
|
4
app/policies/profile_policy.rb
Normal file
4
app/policies/profile_policy.rb
Normal file
@ -0,0 +1,4 @@
|
|||||||
|
class ProfilePolicy < EditOwnPolicy
|
||||||
|
|
||||||
|
|
||||||
|
end
|
@ -15,6 +15,6 @@
|
|||||||
class: "appearance-none border rounded w-full py-2 px-3 text-gray-700 leading-tight focus:outline-none shadow focus:shadow-outline" |
|
class: "appearance-none border rounded w-full py-2 px-3 text-gray-700 leading-tight focus:outline-none shadow focus:shadow-outline" |
|
||||||
.mb-4
|
.mb-4
|
||||||
= f.submit "Resend Confirmation Info", |
|
= f.submit "Resend Confirmation Info", |
|
||||||
class: "button bg-blue-500 hover:bg-blue-700 font-bold text-white focus:outline-none py-2 px-4 rounded focus:shadow-outline w-full" |
|
class: "button bg-cyan-700 hover:bg-cyan-500 font-bold text-white focus:outline-none py-2 px-4 rounded focus:shadow-outline w-full" |
|
||||||
= render "devise/shared/links"
|
= render "devise/shared/links"
|
||||||
= render "devise/shared/form_footer"
|
= render "devise/shared/form_footer"
|
||||||
|
@ -27,6 +27,6 @@
|
|||||||
class: "shadow appearance-none border rounded w-full py-2 px-3 text-gray-700 mb-3 leading-tight focus:outline-none focus:shadow-outline"
|
class: "shadow appearance-none border rounded w-full py-2 px-3 text-gray-700 mb-3 leading-tight focus:outline-none focus:shadow-outline"
|
||||||
.mb-4
|
.mb-4
|
||||||
= f.submit "Change My Password", |
|
= f.submit "Change My Password", |
|
||||||
class: "button bg-blue-500 hover:bg-blue-700 text-white font-bold py-2 px-4 rounded focus:outline-none focus:shadow-outline w-full"
|
class: "button bg-cyan-700 hover:bg-cyan-500 text-white font-bold py-2 px-4 rounded focus:outline-none focus:shadow-outline w-full"
|
||||||
= render "devise/shared/links"
|
= render "devise/shared/links"
|
||||||
= render "devise/shared/form_footer"
|
= render "devise/shared/form_footer"
|
||||||
|
@ -12,6 +12,6 @@
|
|||||||
class: "appearance-none border leading-tight focus:outline-none px-3 py-2 rounded shadow focus:shadow-outline text-gray-700 w-full" |
|
class: "appearance-none border leading-tight focus:outline-none px-3 py-2 rounded shadow focus:shadow-outline text-gray-700 w-full" |
|
||||||
.mb-4
|
.mb-4
|
||||||
= f.submit "Send Password Reset Info", |
|
= f.submit "Send Password Reset Info", |
|
||||||
class: "button bg-blue-500 hover:bg-blue-700 text-white font-bold py-2 px-4 rounded focus:outline-none focus:shadow-outline w-full" |
|
class: "button bg-cyan-700 hover:bg-cyan-500 text-white font-bold py-2 px-4 rounded focus:outline-none focus:shadow-outline w-full" |
|
||||||
= render "devise/shared/links"
|
= render "devise/shared/links"
|
||||||
= render "devise/shared/form_footer"
|
= render "devise/shared/form_footer"
|
||||||
|
@ -33,7 +33,7 @@
|
|||||||
autocomplete: "current-password", |
|
autocomplete: "current-password", |
|
||||||
class: "shadow appearance-none border rounded w-full py-2 px-3 text-gray-700 mb-3 leading-tight focus:outline-none focus:shadow-outline" |
|
class: "shadow appearance-none border rounded w-full py-2 px-3 text-gray-700 mb-3 leading-tight focus:outline-none focus:shadow-outline" |
|
||||||
.actions
|
.actions
|
||||||
= f.submit "Update", class: "button bg-blue-500 hover:bg-blue-700 font-bold text-white focus:outline-none py-2 px-4 rounded focus:shadow-outline w-full"
|
= f.submit "Update", class: "button bg-cyan-700 hover:bg-cyan-500 font-bold text-white focus:outline-none py-2 px-4 rounded focus:shadow-outline w-full"
|
||||||
%p
|
%p
|
||||||
Unhappy?
|
Unhappy?
|
||||||
%span= button_to "Delete my account", registration_path(resource_name), data: { confirm: "Are you sure?" }, method: :delete
|
%span= button_to "Delete my account", registration_path(resource_name), data: { confirm: "Are you sure?" }, method: :delete
|
||||||
|
@ -5,12 +5,6 @@
|
|||||||
html: { class: "bg-white mb-4 px-8 pt-6 pb-8 rounded shadow-md" } ,
|
html: { class: "bg-white mb-4 px-8 pt-6 pb-8 rounded shadow-md" } ,
|
||||||
url: registration_path(resource_name) ) do |f|
|
url: registration_path(resource_name) ) do |f|
|
||||||
= render "devise/shared/error_messages", resource: resource
|
= render "devise/shared/error_messages", resource: resource
|
||||||
.mb-4
|
|
||||||
= f.label :name, class: "block font-bold mb-2 text-gray-700 text-sm"
|
|
||||||
= f.text_field :name,
|
|
||||||
autocomplete: "name",
|
|
||||||
placeholder: "Pekka Juustonen",
|
|
||||||
class: "appearance-none border rounded w-full py-2 px-3 text-gray-700 leading-tight focus:outline-none shadow focus:shadow-outline"
|
|
||||||
.mb-4
|
.mb-4
|
||||||
= f.label :email, class: "block font-bold mb-2 text-gray-700 text-sm"
|
= f.label :email, class: "block font-bold mb-2 text-gray-700 text-sm"
|
||||||
= f.email_field :email,
|
= f.email_field :email,
|
||||||
@ -33,6 +27,6 @@
|
|||||||
class: "appearance-none border leading-tight focus:outline-none px-3 py-2 rounded shadow focus:shadow-outline text-gray-700 w-full" |
|
class: "appearance-none border leading-tight focus:outline-none px-3 py-2 rounded shadow focus:shadow-outline text-gray-700 w-full" |
|
||||||
.mb-4
|
.mb-4
|
||||||
= f.submit "Sign Up", |
|
= f.submit "Sign Up", |
|
||||||
class: "button bg-blue-500 hover:bg-blue-700 font-bold text-white focus:outline-none py-2 px-4 rounded focus:shadow-outline w-full" |
|
class: "button bg-cyan-700 hover:bg-cyan-700 font-bold text-white focus:outline-none py-2 px-4 rounded focus:shadow-outline w-full" |
|
||||||
= render "devise/shared/links"
|
= render "devise/shared/links"
|
||||||
= render "devise/shared/form_footer"
|
= render "devise/shared/form_footer"
|
||||||
|
@ -21,6 +21,6 @@
|
|||||||
class: "align-baseline inline-block text-gray-700 text-sm"
|
class: "align-baseline inline-block text-gray-700 text-sm"
|
||||||
.mb-4
|
.mb-4
|
||||||
= f.submit "Log in",
|
= f.submit "Log in",
|
||||||
class: "button bg-blue-500 hover:bg-blue-700 text-white font-bold py-2 px-4 rounded focus:outline-none focus:shadow-outline w-full"
|
class: "button bg-cyan-700 hover:bg-cyan-500 text-white font-bold py-2 px-4 rounded focus:outline-none focus:shadow-outline w-full"
|
||||||
= render "devise/shared/links"
|
= render "devise/shared/links"
|
||||||
= render "devise/shared/form_footer"
|
= render "devise/shared/form_footer"
|
||||||
|
@ -14,6 +14,6 @@
|
|||||||
class: "appearance-none border leading-tight focus:outline-none px-3 py-2 rounded shadow focus:shadow-outline text-gray-700 w-full" |
|
class: "appearance-none border leading-tight focus:outline-none px-3 py-2 rounded shadow focus:shadow-outline text-gray-700 w-full" |
|
||||||
.mb-4
|
.mb-4
|
||||||
= f.submit "Resend unlock instructions", |
|
= f.submit "Resend unlock instructions", |
|
||||||
class: "button bg-blue-500 hover:bg-blue-700 font-bold text-white focus:outline-none py-2 px-4 rounded focus:shadow-outline w-full" |
|
class: "button bg-cyan-700 hover:bg-cyan-500 font-bold text-white focus:outline-none py-2 px-4 rounded focus:shadow-outline w-full" |
|
||||||
= render "devise/shared/links"
|
= render "devise/shared/links"
|
||||||
= render "devise/shared/form_footer"
|
= render "devise/shared/form_footer"
|
||||||
|
@ -1,16 +1,11 @@
|
|||||||
= simple_form_for @entity do |f|
|
= simple_form_for @entity do |f|
|
||||||
- if @entity.errors.any?
|
= f.error_notification
|
||||||
#error_explanation
|
|
||||||
%h2= "#{pluralize(@entity.errors.count, "error")} prohibited this entity from being saved:"
|
|
||||||
%ul
|
|
||||||
- @entity.errors.full_messages.each do |message|
|
|
||||||
%li= message
|
|
||||||
|
|
||||||
.field
|
|
||||||
= f.input :name
|
= f.input :name
|
||||||
.field
|
|
||||||
= f.input :ha_id , collection: Entity.ha_entities
|
= f.input :ha_id , collection: Entity.ha_entities
|
||||||
.field
|
= f.input :member_id , collection: Member.all.collect{|m| [m.email , m.id ]}
|
||||||
= f.input :member_id , collection: Member.all.collect{|m| [m.name , m.id ]}
|
|
||||||
|
.flex.justify-between.mt-3
|
||||||
.actions{class: button_classes}
|
.actions{class: button_classes}
|
||||||
= f.submit 'Save'
|
= f.submit 'Save'
|
||||||
|
= link_to 'Back', entities_path , class: "mt-3"
|
||||||
|
@ -1,7 +1,5 @@
|
|||||||
%h1 Editing entity
|
.flex.justify-center
|
||||||
|
.flex.flex-col
|
||||||
|
.text-xl.m-4
|
||||||
|
New event
|
||||||
= render 'form'
|
= render 'form'
|
||||||
|
|
||||||
= link_to 'Show', @entity
|
|
||||||
\|
|
|
||||||
= link_to 'Back', entities_path
|
|
||||||
|
@ -1,6 +1,8 @@
|
|||||||
%h1 Listing entities
|
.flex.justify-center
|
||||||
|
%h1.text-3xl Listing entities
|
||||||
|
.flex.justify-center.mt-10
|
||||||
|
|
||||||
%table
|
%table.table-auto.border-separate
|
||||||
%thead
|
%thead
|
||||||
%tr
|
%tr
|
||||||
%th Name
|
%th Name
|
||||||
@ -14,14 +16,15 @@
|
|||||||
%tbody
|
%tbody
|
||||||
- @entities.each do |entity|
|
- @entities.each do |entity|
|
||||||
%tr
|
%tr
|
||||||
%td= entity.name
|
%td.p-2= entity.name
|
||||||
%td= entity.ha_id
|
%td.p-2= entity.ha_id
|
||||||
%td= entity.type
|
%td.p-2= entity.type
|
||||||
%td= entity.member.name
|
%td.p-2= entity.member.email
|
||||||
%td= link_to 'Show', entity
|
%td.p-2= link_to 'Show', entity
|
||||||
%td= link_to 'Edit', edit_entity_path(entity)
|
%td.p-2= link_to 'Edit', edit_entity_path(entity)
|
||||||
%td= link_to 'Destroy', entity, method: :delete, data: { confirm: 'Are you sure?' }
|
%td.p-2= link_to 'Destroy', entity, method: :delete, data: { confirm: 'Are you sure?' }
|
||||||
|
|
||||||
%br
|
|
||||||
|
.flex.justify-center.mt-10
|
||||||
|
|
||||||
= link_to 'New Entity', new_entity_path
|
= link_to 'New Entity', new_entity_path
|
||||||
|
@ -1,7 +1,5 @@
|
|||||||
%h1 New entity
|
.flex.justify-center
|
||||||
|
.column
|
||||||
.grid.grid-cols-3
|
.text-xl.m-4
|
||||||
%div
|
New entity
|
||||||
= render 'form'
|
= render 'form'
|
||||||
|
|
||||||
= link_to 'Back', entities_path
|
|
||||||
|
@ -15,7 +15,7 @@
|
|||||||
= @entity.value
|
= @entity.value
|
||||||
%p
|
%p
|
||||||
%b Member:
|
%b Member:
|
||||||
= @entity.member.name
|
= @entity.member.email
|
||||||
|
|
||||||
= link_to 'Edit', edit_entity_path(@entity)
|
= link_to 'Edit', edit_entity_path(@entity)
|
||||||
\|
|
\|
|
||||||
|
11
app/views/events/_event.haml
Normal file
11
app/views/events/_event.haml
Normal file
@ -0,0 +1,11 @@
|
|||||||
|
%section.overflow-hidden.grid.grid-cols-1.m-5.md:m-12.lg:m-20.md:grid-cols-2
|
||||||
|
%div
|
||||||
|
= image_for( event , "h-56 w-full object-cover sm:h-full")
|
||||||
|
.p-8.md:p-12.lg:px-16.lg:py-24
|
||||||
|
.mx-auto.max-w-xl.text-center
|
||||||
|
%h2.text-2xl.font-bold.md:text-4xl
|
||||||
|
= event.name
|
||||||
|
%h4.text-xl.mt-10.md:text-2xl
|
||||||
|
= event.start_date
|
||||||
|
.mt-8{ prose_classes }
|
||||||
|
= markdown(event.text)
|
16
app/views/events/_form.html.haml
Normal file
16
app/views/events/_form.html.haml
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
= simple_form_for @event do |f|
|
||||||
|
= f.error_notification
|
||||||
|
|
||||||
|
= f.input :name
|
||||||
|
= f.input :text
|
||||||
|
.grid.grid-cols-2.gap-10
|
||||||
|
= f.input :start_date
|
||||||
|
= f.input :end_date
|
||||||
|
= f.input :profile_id , as: :hidden
|
||||||
|
= f.input :picture , as: :file
|
||||||
|
.flex.justify-between
|
||||||
|
%button.mt-6.bg-cyan-200.mr-3.inline-block.rounded-lg.px-4.py-3.text-md.font-medium.border.border-gray-400
|
||||||
|
= f.submit 'Save'
|
||||||
|
= link_to member_path(current_member) do
|
||||||
|
.mt-6.ml-20.mr-3.inline-block.rounded-lg.px-4.py-3.text-md.font-medium.border.border-gray-400
|
||||||
|
Back
|
6
app/views/events/edit.html.haml
Normal file
6
app/views/events/edit.html.haml
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
.flex.justify-center
|
||||||
|
.column
|
||||||
|
.text-xl.m-4
|
||||||
|
Editing event
|
||||||
|
|
||||||
|
= render 'form'
|
12
app/views/events/index.html.haml
Normal file
12
app/views/events/index.html.haml
Normal file
@ -0,0 +1,12 @@
|
|||||||
|
.flex.justify-center
|
||||||
|
.grid.grid-cols-4
|
||||||
|
- @events.each do |event|
|
||||||
|
.fex.flex-col.overflow-hidden.rounded-lg.border.border-gray-100.shadow-sm.m-10
|
||||||
|
=link_to event do
|
||||||
|
= image_for( event , class: "h-60 w-full object-cover")
|
||||||
|
%h3.py-5.text-2xl.bg-gray-100.text-black.font-bold.text-center
|
||||||
|
= event.name
|
||||||
|
%div.h-full
|
||||||
|
.p-5.text-center
|
||||||
|
.m-2.text-sm.leading-relaxed.line-clamp-3{ prose_classes }
|
||||||
|
= shorten markdown(event.text)
|
6
app/views/events/new.html.haml
Normal file
6
app/views/events/new.html.haml
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
.flex.justify-center
|
||||||
|
.column
|
||||||
|
.text-xl.m-4
|
||||||
|
New event
|
||||||
|
|
||||||
|
= render 'form'
|
3
app/views/events/show.html.haml
Normal file
3
app/views/events/show.html.haml
Normal file
@ -0,0 +1,3 @@
|
|||||||
|
= render "event" , event: @event
|
||||||
|
|
||||||
|
= render "profiles/profile" , profile: @event.profile , header: "About the teacher"
|
@ -14,8 +14,8 @@
|
|||||||
%form.w-full
|
%form.w-full
|
||||||
%label.sr-only{:for => "UserEmail"} Email
|
%label.sr-only{:for => "UserEmail"} Email
|
||||||
.p-2.border.border-gray-100.focus-within:ring.sm:flex.sm:items-center.sm:gap-4
|
.p-2.border.border-gray-100.focus-within:ring.sm:flex.sm:items-center.sm:gap-4
|
||||||
%input#UserEmail.w-full.border-none.focus:border-transparent.focus:ring-transparent.sm:text-sm{:placeholder => "jaakko@iki.fi", :type => "email"}/
|
%input.w-full.rounded.focus:border-transparent.focus:ring-transparent.sm:text-sm{:placeholder => "jaakko@iki.fi", :type => "email"}/
|
||||||
%button.w-full.px-6.py-3.mt-1.text-sm.font-bold.tracking-wide.text-white.uppercase.transition-none.bg-teal-500.hover:bg-teal-600.sm:mt-0.sm:w-auto.sm:flex-shrink-0
|
%button.w-full.rounded.px-6.py-3.mt-1.text-sm.font-bold.tracking-wide.text-white.uppercase.bg-cyan-700.hover:bg-cyan-500.sm:mt-0.sm:w-auto.sm:flex-shrink-0
|
||||||
Sign Up
|
Sign Up
|
||||||
.col-span-2.sm:col-span-1
|
.col-span-2.sm:col-span-1
|
||||||
%p.font-medium.text-gray-900 Main
|
%p.font-medium.text-gray-900 Main
|
||||||
|
@ -12,7 +12,7 @@
|
|||||||
= image_tag("fb.webp" , class: "h-10 rounded-md")
|
= image_tag("fb.webp" , class: "h-10 rounded-md")
|
||||||
%li
|
%li
|
||||||
- unless member_signed_in?
|
- unless member_signed_in?
|
||||||
%a.inline-flex.items-center.justify-center.h-12.px-6.font-medium.tracking-wide.text-white.transition.duration-200.rounded-lg.shadow-md.bg-green-800.hover:bg-blue-800.focus:shadow-outline.focus:outline-none{"aria-label" => "Sign up", :href => main_app.member_session_path, :title => "Log in or Sign up"}
|
%a.inline-flex.items-center.justify-center.h-12.px-6.font-medium.tracking-wide.text-white.transition.duration-200.rounded-lg.shadow-md.bg-cyan-700.hover:bg-cyan-500.focus:shadow-outline.focus:outline-none{"aria-label" => "Sign up", :href => main_app.member_session_path, :title => "Log in or Sign up"}
|
||||||
Login
|
Login
|
||||||
- else
|
- else
|
||||||
.inline-flex.items-stretch.rounded-md.border
|
.inline-flex.items-stretch.rounded-md.border
|
||||||
|
@ -3,7 +3,7 @@
|
|||||||
%a.block.rounded-lg.px-4.py-2.text-sm.text-gray-500.hover:bg-gray-50.hover:text-gray-700{:href => "/forum", :role => "menuitem"}
|
%a.block.rounded-lg.px-4.py-2.text-sm.text-gray-500.hover:bg-gray-50.hover:text-gray-700{:href => "/forum", :role => "menuitem"}
|
||||||
Forum
|
Forum
|
||||||
%a.block.rounded-lg.px-4.py-2.text-sm.text-gray-500.hover:bg-gray-50.hover:text-gray-700{:href => main_app.member_path(current_member), :role => "menuitem"}
|
%a.block.rounded-lg.px-4.py-2.text-sm.text-gray-500.hover:bg-gray-50.hover:text-gray-700{:href => main_app.member_path(current_member), :role => "menuitem"}
|
||||||
Profile
|
Settings
|
||||||
- unless Rails.env.production?
|
- unless Rails.env.production?
|
||||||
- if current_member.admin?
|
- if current_member.admin?
|
||||||
%a.block.rounded-lg.px-4.py-2.text-sm.text-gray-500.hover:bg-gray-50.hover:text-gray-700{:href => merged.pages_path(), :role => "menuitem"}
|
%a.block.rounded-lg.px-4.py-2.text-sm.text-gray-500.hover:bg-gray-50.hover:text-gray-700{:href => merged.pages_path(), :role => "menuitem"}
|
||||||
|
@ -1,11 +1,5 @@
|
|||||||
= form_for @member do |f|
|
= simple_form_for @member do |f|
|
||||||
.flex.flex-col
|
= f.error_notification
|
||||||
- if @member.errors.any?
|
|
||||||
#error_explanation
|
|
||||||
%h2= "#{pluralize(@member.errors.count, "error")} prohibited this member from being saved:"
|
|
||||||
%ul
|
|
||||||
- @member.errors.full_messages.each do |message|
|
|
||||||
%li= message
|
|
||||||
|
|
||||||
.grid.grid-cols-2.m-20.gap-10
|
.grid.grid-cols-2.m-20.gap-10
|
||||||
.field
|
.field
|
||||||
|
@ -1,25 +1,14 @@
|
|||||||
|
= paginate @members
|
||||||
.flex.justify-center
|
.flex.justify-center
|
||||||
|
|
||||||
%h1 Listing members
|
.grid.grid-cols-4
|
||||||
|
|
||||||
%table
|
|
||||||
%thead
|
|
||||||
%tr
|
|
||||||
%th Name
|
|
||||||
%th Public
|
|
||||||
%th
|
|
||||||
%th
|
|
||||||
%th
|
|
||||||
|
|
||||||
%tbody
|
|
||||||
- @members.each do |member|
|
- @members.each do |member|
|
||||||
%tr
|
.fex.flex-col.overflow-hidden.rounded-lg.border.border-gray-100.shadow-sm.m-10
|
||||||
%td= member.name
|
=link_to member do
|
||||||
%td= member.public
|
= image_for( member , class: "h-60 w-full object-cover")
|
||||||
%td= link_to 'Show', member
|
%h3.pt-5.text-2xl.bg-gray-100.text-black.font-bold.text-center
|
||||||
%td= link_to 'Edit', edit_member_path(member)
|
= member.name
|
||||||
%td= link_to 'Destroy', member, method: :delete, data: { confirm: 'Are you sure?' }
|
%div.h-full
|
||||||
|
.p-5.text-center
|
||||||
%br
|
.m-2.text-sm.leading-relaxed.line-clamp-3{ prose_classes }
|
||||||
|
= shorten markdown(member.bio)
|
||||||
= link_to 'New Member', new_member_path
|
|
||||||
|
@ -1,33 +1,51 @@
|
|||||||
.px-4.py-16.mx-auto.sm:max-w-xl.md:max-w-full.lg:max-w-screen-xl.md:px-24.lg:px-8.lg:py-20
|
%section.mx-20
|
||||||
.flex.flex-col.max-w-screen-lg.overflow-hidden.bg-white.border.rounded.shadow-sm.lg:flex-row.sm:mx-auto
|
.flex.justify-center
|
||||||
.relative{:class => "lg:w-1/2"}
|
.px-4.py-4.md:py-10.lg:py-16.mx-5.md:mx-12.lg:mx-20.text-center
|
||||||
-if @member.picture_url
|
%h1.text-2xl.font-bold.tracking-tight.sm:text-4xl
|
||||||
= image_tag @member.picture_url, class: "object-cover w-full lg:absolute h-80 lg:h-full"
|
Settings and profiles
|
||||||
.flex.flex-col.justify-center.p-8.lg:p-16.lg:pl-10{:class => "lg:w-1/2"}
|
%h4.text-xl.mt-4.md:text-2xl
|
||||||
|
Allowing you to create and edit various profiles
|
||||||
|
.mt-4.text-lg.pt-4
|
||||||
|
You can have seperate profiles as teacher, artist, or coop member.
|
||||||
|
If you choose to create them they will be publicly listed.
|
||||||
|
Techers and Artists may then create events.
|
||||||
|
|
||||||
|
.grid.grid-cols-2.mx-20
|
||||||
|
.first
|
||||||
|
- Profile.types.each do |kind|
|
||||||
|
.grid.grid-cols-4
|
||||||
|
- if profile = @member.profile(kind)
|
||||||
%div
|
%div
|
||||||
%p.inline-block.px-3.py-px.mb-4.text-xs.font-semibold.tracking-wider.text-teal-900.uppercase.rounded-full.bg-teal-accent-400
|
=profile.Kind
|
||||||
Role ?
|
=link_to profile.name , profile_path(profile) , class: "underline"
|
||||||
%h5.mb-3.text-3xl.font-extrabold.leading-none.sm:text-4xl
|
exists
|
||||||
= @member.name
|
= link_to edit_profile_path(profile) do
|
||||||
.mb-8.text-gray-800
|
|
||||||
.prose= markdown(@member.bio)
|
|
||||||
.flex.items-center
|
|
||||||
%a.inline-flex.items-center.font-semibold.transition-colors.duration-200.text-deep-purple-accent-400.hover:text-deep-purple-800{"aria-label" => "", :href => "/"}
|
|
||||||
Learn More
|
|
||||||
%svg.inline-block.w-3.ml-2{:fill => "currentColor", :viewbox => "0 0 12 12"}
|
|
||||||
%path{:d => "M9.707,5.293l-5-5A1,1,0,0,0,3.293,1.707L7.586,6,3.293,10.293a1,1,0,1,0,1.414,1.414l5-5A1,1,0,0,0,9.707,5.293Z"}
|
|
||||||
|
|
||||||
-if @member == current_member or current_member.admin?
|
|
||||||
|
|
||||||
.flex.justify-around
|
|
||||||
= link_to edit_member_path(@member) do
|
|
||||||
%button.bg-cyan-200.mr-3.inline-block.rounded-lg.px-4.py-3.text-md.font-medium.border.border-gray-400
|
%button.bg-cyan-200.mr-3.inline-block.rounded-lg.px-4.py-3.text-md.font-medium.border.border-gray-400
|
||||||
Edit
|
Edit
|
||||||
.grid.grid-cols-3.gap-4
|
= link_to new_event_path(profile: profile.kind) do
|
||||||
|
%button.bg-cyan-200.mr-3.inline-block.rounded-lg.px-4.py-3.text-md.font-medium.border.border-gray-400
|
||||||
|
New #{profile.Kind} Event
|
||||||
|
-if event = profile.events.length >0
|
||||||
|
%div
|
||||||
|
=link_to profile.events.first.name , event_path(profile.events.first) , class: "underline"
|
||||||
|
= link_to edit_event_path(profile.events.first) do
|
||||||
|
%button.bg-cyan-200.mr-3.inline-block.rounded-lg.px-4.py-3.text-md.font-medium.border.border-gray-400
|
||||||
|
Edit
|
||||||
|
-else
|
||||||
|
No events
|
||||||
|
-else
|
||||||
|
%div Create new profile as
|
||||||
|
= link_to new_profile_path(kind: kind) do
|
||||||
|
%button.bg-cyan-200.mr-3.inline-block.rounded-lg.px-4.py-3.text-md.font-medium.border.border-gray-400
|
||||||
|
= kind.capitalize
|
||||||
|
%div Create profile first
|
||||||
|
%div No events, create profile first
|
||||||
|
|
||||||
|
.grid.grid-cols-6.gap-4.mt-10.mx-10
|
||||||
-@member.entities.each do |entity|
|
-@member.entities.each do |entity|
|
||||||
%div= entity.type
|
%div= entity.type
|
||||||
%div= entity.name
|
%div= entity.name
|
||||||
%div= entity.value
|
%div= entity.value
|
||||||
= form_tag( destroy_member_session_path , {method: :delete } ) do
|
= form_tag( destroy_member_session_path , {method: :delete } ) do
|
||||||
%button.bg-cyan-200.mr-3.inline-block.rounded-lg.px-4.py-3.text-md.font-medium.border.border-gray-400{type: :submit}
|
%button.mt-10.ml-10.bg-cyan-200.mr-3.inline-block.rounded-lg.px-4.py-3.text-md.font-medium.border.border-gray-400{type: :submit}
|
||||||
Sign out
|
Sign out
|
||||||
|
14
app/views/profiles/_form.html.haml
Normal file
14
app/views/profiles/_form.html.haml
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
= simple_form_for @profile do |f|
|
||||||
|
= f.error_notification
|
||||||
|
|
||||||
|
= f.input :name
|
||||||
|
= f.input :bio
|
||||||
|
= f.input :kind, :as => :hidden
|
||||||
|
= f.input :picture , as: :file , label: (@profile.picture.blank? ? "Add picture" : "Change picture (optional)")
|
||||||
|
|
||||||
|
.flex.justify-between.mt-4
|
||||||
|
%button.bg-cyan-200{class: button_classes}
|
||||||
|
= f.submit 'Save'
|
||||||
|
|
||||||
|
%button.bg-cyan-200{class: button_classes}
|
||||||
|
= link_to 'Cancel', member_path(current_member)
|
14
app/views/profiles/_profile.haml
Normal file
14
app/views/profiles/_profile.haml
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
.px-4.py-16.mx-auto.sm:max-w-xl.md:max-w-full.lg:max-w-screen-xl.md:px-24.lg:px-8.lg:py-20
|
||||||
|
.flex.justify-center
|
||||||
|
.px-4.py-4.text-center
|
||||||
|
%h1.text-2xl.font-bold.tracking-tight.sm:text-4xl
|
||||||
|
= header
|
||||||
|
.flex.mt-6.py-4.flex-col.max-w-screen-lg.overflow-hidden.bg-white.border.rounded.shadow-sm.lg:flex-row.sm:mx-auto
|
||||||
|
.relative{:class => "lg:w-1/2"}
|
||||||
|
-if profile.picture_url
|
||||||
|
= image_tag profile.picture_url, class: "object-cover w-full lg:absolute h-80 lg:h-full"
|
||||||
|
.flex.flex-col.justify-center.p-8.lg:p-16.lg:pl-10{:class => "lg:w-1/2"}
|
||||||
|
%h5.mb-3.text-3xl.font-extrabold.leading-none.sm:text-4xl
|
||||||
|
= profile.name
|
||||||
|
.mb-8.text-gray-800
|
||||||
|
.prose= markdown(profile.bio)
|
7
app/views/profiles/edit.html.haml
Normal file
7
app/views/profiles/edit.html.haml
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
.flex.justify-center
|
||||||
|
.column
|
||||||
|
.text-xl.m-4
|
||||||
|
Edit your
|
||||||
|
=@profile.Kind
|
||||||
|
profile
|
||||||
|
= render 'form'
|
14
app/views/profiles/index.html.haml
Normal file
14
app/views/profiles/index.html.haml
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
= paginate @profiles
|
||||||
|
.flex.justify-center
|
||||||
|
|
||||||
|
.grid.grid-cols-4
|
||||||
|
- @profiles.each do |profile|
|
||||||
|
.fex.flex-col.overflow-hidden.rounded-lg.border.border-gray-100.shadow-sm.m-10
|
||||||
|
=link_to profile do
|
||||||
|
= image_for( profile , class: "h-60 w-full object-cover")
|
||||||
|
%h3.py-5.text-2xl.bg-gray-100.text-black.font-bold.text-center
|
||||||
|
= profile.name
|
||||||
|
%div.h-full
|
||||||
|
.p-5.text-center
|
||||||
|
.m-2.text-sm.leading-relaxed.line-clamp-3{ prose_classes }
|
||||||
|
= shorten markdown(profile.bio)
|
7
app/views/profiles/new.html.haml
Normal file
7
app/views/profiles/new.html.haml
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
.flex.justify-center
|
||||||
|
.column
|
||||||
|
.text-xl.m-4
|
||||||
|
Create your
|
||||||
|
=@profile.kind.capitalize
|
||||||
|
profile
|
||||||
|
= render 'form'
|
1
app/views/profiles/show.html.haml
Normal file
1
app/views/profiles/show.html.haml
Normal file
@ -0,0 +1 @@
|
|||||||
|
= render "profile" , profile: @profile , header: "#{@profile.Kind} profile"
|
@ -14,7 +14,7 @@ SimpleForm.setup do |config|
|
|||||||
# stack. The options given below are used to wrap the
|
# stack. The options given below are used to wrap the
|
||||||
# whole input.
|
# whole input.
|
||||||
|
|
||||||
config.wrappers :default, tag: 'div', class: '', error_class: '', valid_class: '' do |b|
|
config.wrappers :default, tag: 'div', class: 'mt-4', error_class: '', valid_class: '' do |b|
|
||||||
b.use :html5
|
b.use :html5
|
||||||
b.use :placeholder
|
b.use :placeholder
|
||||||
b.optional :maxlength
|
b.optional :maxlength
|
||||||
|
@ -1,4 +1,6 @@
|
|||||||
Rails.application.routes.draw do
|
Rails.application.routes.draw do
|
||||||
|
resources :events
|
||||||
|
resources :profiles
|
||||||
resources :entities
|
resources :entities
|
||||||
|
|
||||||
devise_for :members
|
devise_for :members
|
||||||
|
17
db/migrate/20230115120517_create_profiles.rb
Normal file
17
db/migrate/20230115120517_create_profiles.rb
Normal file
@ -0,0 +1,17 @@
|
|||||||
|
class CreateProfiles < ActiveRecord::Migration[7.0]
|
||||||
|
def change
|
||||||
|
create_table :profiles do |t|
|
||||||
|
t.string :name , null: false
|
||||||
|
t.string :kind , null: false
|
||||||
|
t.text :bio , null: false
|
||||||
|
t.string :picture , null: false
|
||||||
|
t.references :member, null: false, foreign_key: true
|
||||||
|
|
||||||
|
t.timestamps
|
||||||
|
end
|
||||||
|
remove_column :members, :name, :string
|
||||||
|
remove_column :members, :bio, :text
|
||||||
|
remove_column :members, :picture, :string
|
||||||
|
remove_column :members, :public, :boolean
|
||||||
|
end
|
||||||
|
end
|
14
db/migrate/20230116120518_create_events.rb
Normal file
14
db/migrate/20230116120518_create_events.rb
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
class CreateEvents < ActiveRecord::Migration[7.0]
|
||||||
|
def change
|
||||||
|
create_table :events do |t|
|
||||||
|
t.string :name , null: false
|
||||||
|
t.text :text , null: false
|
||||||
|
t.date :start_date , null: false
|
||||||
|
t.date :end_date
|
||||||
|
t.references :profile, null: false, foreign_key: true
|
||||||
|
t.string :picture , null: false
|
||||||
|
|
||||||
|
t.timestamps
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
31
db/schema.rb
generated
31
db/schema.rb
generated
@ -10,7 +10,7 @@
|
|||||||
#
|
#
|
||||||
# It's strongly recommended that you check this file into your version control system.
|
# It's strongly recommended that you check this file into your version control system.
|
||||||
|
|
||||||
ActiveRecord::Schema[7.0].define(version: 2023_01_13_170732) do
|
ActiveRecord::Schema[7.0].define(version: 2023_01_16_120518) do
|
||||||
# These are extensions that must be enabled in order to support this database
|
# These are extensions that must be enabled in order to support this database
|
||||||
enable_extension "plpgsql"
|
enable_extension "plpgsql"
|
||||||
|
|
||||||
@ -24,6 +24,18 @@ ActiveRecord::Schema[7.0].define(version: 2023_01_13_170732) do
|
|||||||
t.index ["member_id"], name: "index_entities_on_member_id"
|
t.index ["member_id"], name: "index_entities_on_member_id"
|
||||||
end
|
end
|
||||||
|
|
||||||
|
create_table "events", force: :cascade do |t|
|
||||||
|
t.string "name", null: false
|
||||||
|
t.text "text", null: false
|
||||||
|
t.date "start_date", null: false
|
||||||
|
t.date "end_date"
|
||||||
|
t.bigint "profile_id", null: false
|
||||||
|
t.string "picture", null: false
|
||||||
|
t.datetime "created_at", null: false
|
||||||
|
t.datetime "updated_at", null: false
|
||||||
|
t.index ["profile_id"], name: "index_events_on_profile_id"
|
||||||
|
end
|
||||||
|
|
||||||
create_table "friendly_id_slugs", force: :cascade do |t|
|
create_table "friendly_id_slugs", force: :cascade do |t|
|
||||||
t.string "slug", null: false
|
t.string "slug", null: false
|
||||||
t.integer "sluggable_id", null: false
|
t.integer "sluggable_id", null: false
|
||||||
@ -37,10 +49,6 @@ ActiveRecord::Schema[7.0].define(version: 2023_01_13_170732) do
|
|||||||
end
|
end
|
||||||
|
|
||||||
create_table "members", force: :cascade do |t|
|
create_table "members", force: :cascade do |t|
|
||||||
t.string "name"
|
|
||||||
t.string "bio"
|
|
||||||
t.string "picture"
|
|
||||||
t.boolean "public"
|
|
||||||
t.datetime "created_at", null: false
|
t.datetime "created_at", null: false
|
||||||
t.datetime "updated_at", null: false
|
t.datetime "updated_at", null: false
|
||||||
t.string "email", default: "", null: false
|
t.string "email", default: "", null: false
|
||||||
@ -56,6 +64,17 @@ ActiveRecord::Schema[7.0].define(version: 2023_01_13_170732) do
|
|||||||
t.index ["reset_password_token"], name: "index_members_on_reset_password_token", unique: true
|
t.index ["reset_password_token"], name: "index_members_on_reset_password_token", unique: true
|
||||||
end
|
end
|
||||||
|
|
||||||
|
create_table "profiles", force: :cascade do |t|
|
||||||
|
t.string "name", null: false
|
||||||
|
t.string "kind", null: false
|
||||||
|
t.text "bio", null: false
|
||||||
|
t.string "picture", null: false
|
||||||
|
t.bigint "member_id", null: false
|
||||||
|
t.datetime "created_at", null: false
|
||||||
|
t.datetime "updated_at", null: false
|
||||||
|
t.index ["member_id"], name: "index_profiles_on_member_id"
|
||||||
|
end
|
||||||
|
|
||||||
create_table "thredded_categories", force: :cascade do |t|
|
create_table "thredded_categories", force: :cascade do |t|
|
||||||
t.bigint "messageboard_id", null: false
|
t.bigint "messageboard_id", null: false
|
||||||
t.text "name", null: false
|
t.text "name", null: false
|
||||||
@ -288,6 +307,8 @@ ActiveRecord::Schema[7.0].define(version: 2023_01_13_170732) do
|
|||||||
end
|
end
|
||||||
|
|
||||||
add_foreign_key "entities", "members"
|
add_foreign_key "entities", "members"
|
||||||
|
add_foreign_key "events", "profiles"
|
||||||
|
add_foreign_key "profiles", "members"
|
||||||
add_foreign_key "thredded_messageboard_users", "thredded_messageboards", on_delete: :cascade
|
add_foreign_key "thredded_messageboard_users", "thredded_messageboards", on_delete: :cascade
|
||||||
add_foreign_key "thredded_messageboard_users", "thredded_user_details", on_delete: :cascade
|
add_foreign_key "thredded_messageboard_users", "thredded_user_details", on_delete: :cascade
|
||||||
add_foreign_key "thredded_user_post_notifications", "members", column: "user_id", on_delete: :cascade
|
add_foreign_key "thredded_user_post_notifications", "members", column: "user_id", on_delete: :cascade
|
||||||
|
17
test/fixtures/events.yml
vendored
Normal file
17
test/fixtures/events.yml
vendored
Normal file
@ -0,0 +1,17 @@
|
|||||||
|
# Read about fixtures at https://api.rubyonrails.org/classes/ActiveRecord/FixtureSet.html
|
||||||
|
|
||||||
|
one:
|
||||||
|
name: MyString
|
||||||
|
text: MyText
|
||||||
|
start_date: 2023-01-16
|
||||||
|
end_date: 2023-01-16
|
||||||
|
profile: one
|
||||||
|
picture: MyString
|
||||||
|
|
||||||
|
two:
|
||||||
|
name: MyString
|
||||||
|
text: MyText
|
||||||
|
start_date: 2023-01-16
|
||||||
|
end_date: 2023-01-16
|
||||||
|
profile: two
|
||||||
|
picture: MyString
|
13
test/fixtures/profiles.yml
vendored
Normal file
13
test/fixtures/profiles.yml
vendored
Normal file
@ -0,0 +1,13 @@
|
|||||||
|
# Read about fixtures at https://api.rubyonrails.org/classes/ActiveRecord/FixtureSet.html
|
||||||
|
|
||||||
|
one:
|
||||||
|
name: MyString
|
||||||
|
bio: MyString
|
||||||
|
picture: MyString
|
||||||
|
member: one
|
||||||
|
|
||||||
|
two:
|
||||||
|
name: MyString
|
||||||
|
bio: MyString
|
||||||
|
picture: MyString
|
||||||
|
member: two
|
7
test/models/event_test.rb
Normal file
7
test/models/event_test.rb
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
require "test_helper"
|
||||||
|
|
||||||
|
class EventTest < ActiveSupport::TestCase
|
||||||
|
# test "the truth" do
|
||||||
|
# assert true
|
||||||
|
# end
|
||||||
|
end
|
7
test/models/teacher_test.rb
Normal file
7
test/models/teacher_test.rb
Normal file
@ -0,0 +1,7 @@
|
|||||||
|
require "test_helper"
|
||||||
|
|
||||||
|
class ProfileTest < ActiveSupport::TestCase
|
||||||
|
# test "the truth" do
|
||||||
|
# assert true
|
||||||
|
# end
|
||||||
|
end
|
18
test/policies/event_policy_test.rb
Normal file
18
test/policies/event_policy_test.rb
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
require 'test_helper'
|
||||||
|
|
||||||
|
class EventPolicyTest < ActiveSupport::TestCase
|
||||||
|
def test_scope
|
||||||
|
end
|
||||||
|
|
||||||
|
def test_show
|
||||||
|
end
|
||||||
|
|
||||||
|
def test_create
|
||||||
|
end
|
||||||
|
|
||||||
|
def test_update
|
||||||
|
end
|
||||||
|
|
||||||
|
def test_destroy
|
||||||
|
end
|
||||||
|
end
|
18
test/policies/member_policy_test.rb
Normal file
18
test/policies/member_policy_test.rb
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
require 'test_helper'
|
||||||
|
|
||||||
|
class MemberPolicyTest < ActiveSupport::TestCase
|
||||||
|
def test_scope
|
||||||
|
end
|
||||||
|
|
||||||
|
def test_show
|
||||||
|
end
|
||||||
|
|
||||||
|
def test_create
|
||||||
|
end
|
||||||
|
|
||||||
|
def test_update
|
||||||
|
end
|
||||||
|
|
||||||
|
def test_destroy
|
||||||
|
end
|
||||||
|
end
|
51
test/system/events_test.rb
Normal file
51
test/system/events_test.rb
Normal file
@ -0,0 +1,51 @@
|
|||||||
|
require "application_system_test_case"
|
||||||
|
|
||||||
|
class EventsTest < ApplicationSystemTestCase
|
||||||
|
setup do
|
||||||
|
@event = events(:one)
|
||||||
|
end
|
||||||
|
|
||||||
|
test "visiting the index" do
|
||||||
|
visit events_url
|
||||||
|
assert_selector "h1", text: "Events"
|
||||||
|
end
|
||||||
|
|
||||||
|
test "should create event" do
|
||||||
|
visit events_url
|
||||||
|
click_on "New event"
|
||||||
|
|
||||||
|
fill_in "End date", with: @event.end_date
|
||||||
|
fill_in "Name", with: @event.name
|
||||||
|
fill_in "Picture", with: @event.picture
|
||||||
|
fill_in "Profile", with: @event.profile_id
|
||||||
|
fill_in "Start date", with: @event.start_date
|
||||||
|
fill_in "Text", with: @event.text
|
||||||
|
click_on "Create Event"
|
||||||
|
|
||||||
|
assert_text "Event was successfully created"
|
||||||
|
click_on "Back"
|
||||||
|
end
|
||||||
|
|
||||||
|
test "should update Event" do
|
||||||
|
visit event_url(@event)
|
||||||
|
click_on "Edit this event", match: :first
|
||||||
|
|
||||||
|
fill_in "End date", with: @event.end_date
|
||||||
|
fill_in "Name", with: @event.name
|
||||||
|
fill_in "Picture", with: @event.picture
|
||||||
|
fill_in "Profile", with: @event.profile_id
|
||||||
|
fill_in "Start date", with: @event.start_date
|
||||||
|
fill_in "Text", with: @event.text
|
||||||
|
click_on "Update Event"
|
||||||
|
|
||||||
|
assert_text "Event was successfully updated"
|
||||||
|
click_on "Back"
|
||||||
|
end
|
||||||
|
|
||||||
|
test "should destroy Event" do
|
||||||
|
visit event_url(@event)
|
||||||
|
click_on "Destroy this event", match: :first
|
||||||
|
|
||||||
|
assert_text "Event was successfully destroyed"
|
||||||
|
end
|
||||||
|
end
|
47
test/system/profiles_test.rb
Normal file
47
test/system/profiles_test.rb
Normal file
@ -0,0 +1,47 @@
|
|||||||
|
require "application_system_test_case"
|
||||||
|
|
||||||
|
class ProfilesTest < ApplicationSystemTestCase
|
||||||
|
setup do
|
||||||
|
@profile = profiles(:one)
|
||||||
|
end
|
||||||
|
|
||||||
|
test "visiting the index" do
|
||||||
|
visit profiles_url
|
||||||
|
assert_selector "h1", text: "Profiles"
|
||||||
|
end
|
||||||
|
|
||||||
|
test "should create profile" do
|
||||||
|
visit profiles_url
|
||||||
|
click_on "New profile"
|
||||||
|
|
||||||
|
fill_in "Bio", with: @profile.bio
|
||||||
|
fill_in "Member", with: @profile.member_id
|
||||||
|
fill_in "Name", with: @profile.name
|
||||||
|
fill_in "Picture", with: @profile.picture
|
||||||
|
click_on "Create Profile"
|
||||||
|
|
||||||
|
assert_text "Profile was successfully created"
|
||||||
|
click_on "Back"
|
||||||
|
end
|
||||||
|
|
||||||
|
test "should update Profile" do
|
||||||
|
visit profile_url(@profile)
|
||||||
|
click_on "Edit this profile", match: :first
|
||||||
|
|
||||||
|
fill_in "Bio", with: @profile.bio
|
||||||
|
fill_in "Member", with: @profile.member_id
|
||||||
|
fill_in "Name", with: @profile.name
|
||||||
|
fill_in "Picture", with: @profile.picture
|
||||||
|
click_on "Update Profile"
|
||||||
|
|
||||||
|
assert_text "Profile was successfully updated"
|
||||||
|
click_on "Back"
|
||||||
|
end
|
||||||
|
|
||||||
|
test "should destroy Profile" do
|
||||||
|
visit profile_url(@profile)
|
||||||
|
click_on "Destroy this profile", match: :first
|
||||||
|
|
||||||
|
assert_text "Profile was successfully destroyed"
|
||||||
|
end
|
||||||
|
end
|
Reference in New Issue
Block a user