Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Dl/uniform forms #107

Merged
merged 4 commits into from
Sep 5, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
7 changes: 4 additions & 3 deletions app/controllers/achievements_controller.rb
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,12 @@ class AchievementsController < ApplicationController
before_action :authenticate_user!, except: [:index, :show]

def index
@achievements = Achievement.order(date: :desc)
# Scope achievements to the current user
@achievements = current_user.achievements.order(date: :desc)
end

def show
@achievement = Achievement.find(params[:id])
@achievement = current_user.achievements.find(params[:id])
AchievementView.create(
achievement: @achievement,
user: @achievement.user,
Expand Down Expand Up @@ -61,4 +62,4 @@ def destroy
def achievement_params
params.require(:achievement).permit(:title, :date, :description, :icon, :url)
end
end
end
22 changes: 11 additions & 11 deletions app/controllers/links_controller.rb
Original file line number Diff line number Diff line change
@@ -1,13 +1,14 @@
class LinksController < ApplicationController
before_action :authenticate_user!, except: [:index, :show, :user_links, :track_click]
before_action :set_theme, only: [:user_links] # Add this line
before_action :set_theme, only: [:user_links]

def index
@links = Link.order(:position)
# Scope links to the current user
@links = current_user.links.order(:position)
end

def show
@link = Link.find(params[:id])
@link = current_user.links.find(params[:id])
end

def new
Expand Down Expand Up @@ -45,17 +46,17 @@ def destroy
def user_links
@user = User.find_by(username: params[:username])
return redirect_to root_path, alert: "User not found" if @user.nil?
@links = @user.links.where(hidden: false, visible: true)
@hidden_links = @user.links.where(hidden: true)
@pinned_links = @user.links.where(pinned: true)

@links = @user.links.visible
@hidden_links = @user.links.hidden
@pinned_links = @user.links.pinned
@achievements = @user.achievements
@user.tags = JSON.parse(@user.tags) if @user.tags.is_a?(String)

# Add debugging
Rails.logger.debug "Theme: #{@theme.inspect}"
Rails.logger.debug "Hidden Links: #{@hidden_links.inspect}"

# Render the appropriate template based on the theme
case @theme
when 'retro'
Expand Down Expand Up @@ -90,7 +91,6 @@ def link_params
end

def set_theme
# Determine the theme either from a query parameter or route segment
@theme = params[:theme] || 'default'
end
end
end
41 changes: 31 additions & 10 deletions app/controllers/users/registrations_controller.rb
Original file line number Diff line number Diff line change
@@ -1,7 +1,14 @@
class Users::RegistrationsController < Devise::RegistrationsController
before_action :configure_permitted_parameters, if: :devise_controller?
before_action :check_signups_enabled, only: [:create]

def create
# Check if sign-ups are disabled and no valid invite code is provided
unless Rails.application.config.sign_ups_open || valid_invite_code?(params[:user][:invite_code])
redirect_to root_path, alert: "Sign-ups are currently disabled."
return
end

build_resource(sign_up_params)

resource.tags = JSON.parse(resource.tags) if resource.tags.is_a?(String)
Expand Down Expand Up @@ -34,37 +41,51 @@ def edit
def update
@user = current_user
@user.tags = JSON.parse(@user.tags) if @user.tags.is_a?(String)

# Check if password or email is being updated

is_password_change = params[:user][:password].present? || params[:user][:password_confirmation].present?
is_email_change = params[:user][:email].present? && params[:user][:email] != @user.email

if is_password_change || is_email_change
# Require current password for sensitive changes
successfully_updated = @user.update_with_password(account_update_params)
else
# Do not require current password for non-sensitive changes
params[:user].delete(:current_password)
successfully_updated = @user.update_without_password(account_update_params)
end

if successfully_updated
bypass_sign_in(@user) # Sign in the user bypassing validation
bypass_sign_in(@user)
redirect_to edit_user_registration_path, notice: 'Profile updated successfully'
else
render :edit
end
end

private

def check_signups_enabled
# Check if sign-ups are disabled and no valid invite code is provided
if !Rails.application.config.sign_ups_open && (params[:user].blank? || !valid_invite_code?(params[:user][:invite_code]))
redirect_to root_path, alert: "Sign-ups are currently disabled."
end
end

def valid_invite_code?(invite_code)
# List of valid invite codes
valid_codes = ["POWEROVERWHELMING", "SWORDFISH", "HUNTER2"]

# Check if the provided invite code matches any of the valid codes, case-insensitive
valid_codes.any? { |code| code.casecmp(invite_code).zero? }
end

protected

def configure_permitted_parameters
devise_parameter_sanitizer.permit(:sign_up, keys: [:email, :password, :password_confirmation, :username, :full_name, :tags, :avatar, :banner, :description, :banner_enabled, :avatar_border])
devise_parameter_sanitizer.permit(:sign_up, keys: [:email, :password, :password_confirmation, :username, :full_name, :tags, :avatar, :banner, :description, :banner_enabled, :avatar_border, :invite_code])
devise_parameter_sanitizer.permit(:account_update, keys: [:email, :password, :password_confirmation, :username, :full_name, :tags, :avatar, :banner, :description, :banner_enabled, :avatar_border])
end

def sign_up_params
params.require(:user).permit(:email, :password, :password_confirmation, :username, :full_name, :tags, :avatar, :banner, :description, :banner_enabled, :avatar_border).tap do |user_params|
params.require(:user).permit(:email, :password, :password_confirmation, :username, :full_name, :tags, :avatar, :banner, :description, :banner_enabled, :avatar_border, :invite_code).tap do |user_params|
user_params[:tags] = user_params[:tags].split(',').map(&:strip).to_json if user_params[:tags].present?
end
end
Expand All @@ -74,4 +95,4 @@ def account_update_params
user_params[:tags] = user_params[:tags].split(',').map(&:strip).to_json if user_params[:tags].present?
end
end
end
end
1 change: 1 addition & 0 deletions app/models/user.rb
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
# app/models/user.rb
class User < ApplicationRecord
attr_accessor :invite_code
devise :database_authenticatable, :registerable,
:recoverable, :rememberable, :validatable

Expand Down
13 changes: 10 additions & 3 deletions app/services/open_graph_image_generator.rb
Original file line number Diff line number Diff line change
Expand Up @@ -54,10 +54,17 @@ def generate
def download_image(url)
tempfile = Tempfile.new(['avatar', '.jpg'])
tempfile.binmode
URI.open(url) do |image|
tempfile.write(image.read)
begin
URI.open(url) do |image|
tempfile.write(image.read)
end
rescue OpenURI::HTTPError, Errno::ENOENT, SocketError => e
Rails.logger.error("Failed to download image from URL: #{url}. Error: #{e.message}. Using default image.")
# Use a default image if the download fails
default_image_path = Rails.root.join('app', 'assets', 'images', 'greg.jpg')
tempfile.write(File.read(default_image_path))
end
tempfile.rewind
MiniMagick::Image.open(tempfile.path)
end
end
end
6 changes: 5 additions & 1 deletion app/views/achievements/_form.html.erb
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
<%= form_with(model: achievement, local: true, class: "max-w-md mx-auto p-4 bg-gray-800 rounded-lg shadow-md") do |form| %>
<%= form_with(model: achievement, local: true, class: "max-w-2xl mx-auto p-6 bg-gray-800 rounded-lg shadow-md") do |form| %>
<% if achievement.errors.any? %>
<div id="error_explanation" class="bg-red-100 border-l-4 border-red-500 text-red-700 p-4 mb-4 rounded">
<h2 class="font-bold mb-2"><%= pluralize(achievement.errors.count, 'error') %> prohibited this achievement from being saved:</h2>
Expand Down Expand Up @@ -39,3 +39,7 @@
<%= form.submit 'Save', class: 'bg-lime-500 hover:bg-lime-700 text-white font-bold py-2 px-4 rounded transition duration-300 ease-in-out' %>
</div>
<% end %>

<div class="mt-4 text-center">
<%= link_to 'Back', achievements_path, class: 'text-lime-300 hover:text-lime-100 transition duration-300 ease-in-out' %>
</div>
2 changes: 1 addition & 1 deletion app/views/achievements/edit.html.erb
Original file line number Diff line number Diff line change
@@ -1,3 +1,3 @@
<h1>Edit achievement</h1>
<%= render 'form', achievement: @achievement %>
<%= link_to 'Back', achievements_path, class: 'text-white hover:text-lime-300' %>

1 change: 0 additions & 1 deletion app/views/achievements/new.html.erb
Original file line number Diff line number Diff line change
@@ -1,3 +1,2 @@
<h1>New Achievement</h1>
<%= render 'form', achievement: @achievement %>
<%= link_to 'Back', achievements_path, class: 'text-white hover:text-lime-300' %>
28 changes: 16 additions & 12 deletions app/views/devise/confirmations/new.html.erb
Original file line number Diff line number Diff line change
@@ -1,16 +1,20 @@
<h2>Resend confirmation instructions</h2>
<div class="max-w-2xl mx-auto p-6 bg-gray-800 rounded-lg shadow-md">
<h2 class="text-2xl font-bold mb-6 text-lime-200">Resend confirmation instructions</h2>

<%= form_for(resource, as: resource_name, url: confirmation_path(resource_name), html: { method: :post }) do |f| %>
<%= render "devise/shared/error_messages", resource: resource %>
<%= form_for(resource, as: resource_name, url: confirmation_path(resource_name), html: { method: :post, class: "space-y-6" }) do |f| %>
<%= render "devise/shared/error_messages", resource: resource %>

<div class="field">
<%= f.label :email %><br />
<%= f.email_field :email, autofocus: true, autocomplete: "email", value: (resource.pending_reconfirmation? ? resource.unconfirmed_email : resource.email) %>
</div>
<div>
<%= f.label :email, class: 'block text-lime-200 font-semibold mb-2' %>
<%= f.email_field :email, autofocus: true, autocomplete: "email", value: (resource.pending_reconfirmation? ? resource.unconfirmed_email : resource.email), class: 'block w-full px-4 py-2 border border-gray-700 rounded bg-gray-900 text-white focus:outline-none focus:border-lime-500' %>
</div>

<div class="actions">
<%= f.submit "Resend confirmation instructions" %>
</div>
<% end %>
<div class="actions text-center">
<%= f.submit "Resend confirmation instructions", class: 'bg-lime-500 hover:bg-lime-600 text-white font-bold py-2 px-4 rounded transition duration-300 ease-in-out focus:outline-none' %>
</div>
<% end %>

<%= render "devise/shared/links" %>
<div class="mt-4 text-center">
<%= render "devise/shared/links" %>
</div>
</div>
44 changes: 24 additions & 20 deletions app/views/devise/passwords/edit.html.erb
Original file line number Diff line number Diff line change
@@ -1,25 +1,29 @@
<h2>Change your password</h2>
<div class="max-w-2xl mx-auto p-6 bg-gray-800 rounded-lg shadow-md">
<h2 class="text-2xl font-bold mb-6 text-lime-200">Change your password</h2>

<%= form_for(resource, as: resource_name, url: password_path(resource_name), html: { method: :put }) do |f| %>
<%= render "devise/shared/error_messages", resource: resource %>
<%= f.hidden_field :reset_password_token %>
<%= form_for(resource, as: resource_name, url: password_path(resource_name), html: { method: :put, class: "space-y-6" }) do |f| %>
<%= render "devise/shared/error_messages", resource: resource %>
<%= f.hidden_field :reset_password_token %>

<div class="field">
<%= f.label :password, "New password" %><br />
<% if @minimum_password_length %>
<em>(<%= @minimum_password_length %> characters minimum)</em><br />
<% end %>
<%= f.password_field :password, autofocus: true, autocomplete: "new-password" %>
</div>
<div>
<%= f.label :password, "New password", class: 'block text-lime-200 font-semibold mb-2' %>
<% if @minimum_password_length %>
<em class="text-gray-400 text-sm">(<%= @minimum_password_length %> characters minimum)</em>
<% end %>
<%= f.password_field :password, autofocus: true, autocomplete: "new-password", class: 'block w-full px-4 py-2 border border-gray-700 rounded bg-gray-900 text-white focus:outline-none focus:border-lime-500' %>
</div>

<div class="field">
<%= f.label :password_confirmation, "Confirm new password" %><br />
<%= f.password_field :password_confirmation, autocomplete: "new-password" %>
</div>
<div>
<%= f.label :password_confirmation, "Confirm new password", class: 'block text-lime-200 font-semibold mb-2' %>
<%= f.password_field :password_confirmation, autocomplete: "new-password", class: 'block w-full px-4 py-2 border border-gray-700 rounded bg-gray-900 text-white focus:outline-none focus:border-lime-500' %>
</div>

<div class="actions">
<%= f.submit "Change my password" %>
</div>
<% end %>
<div class="actions text-center">
<%= f.submit "Change my password", class: 'bg-lime-500 hover:bg-lime-600 text-white font-bold py-2 px-4 rounded transition duration-300 ease-in-out focus:outline-none' %>
</div>
<% end %>

<%= render "devise/shared/links" %>
<div class="mt-4 text-center">
<%= render "devise/shared/links" %>
</div>
</div>
28 changes: 16 additions & 12 deletions app/views/devise/passwords/new.html.erb
Original file line number Diff line number Diff line change
@@ -1,16 +1,20 @@
<h2>Forgot your password?</h2>
<div class="max-w-2xl mx-auto p-6 bg-gray-800 rounded-lg shadow-md">
<h2 class="text-2xl font-bold mb-6 text-lime-200">Forgot your password?</h2>

<%= form_for(resource, as: resource_name, url: password_path(resource_name), html: { method: :post }) do |f| %>
<%= render "devise/shared/error_messages", resource: resource %>
<%= form_for(resource, as: resource_name, url: password_path(resource_name), html: { method: :post, class: "space-y-6" }) do |f| %>
<%= render "devise/shared/error_messages", resource: resource %>

<div class="field">
<%= f.label :email %><br />
<%= f.email_field :email, autofocus: true, autocomplete: "email" %>
</div>
<div>
<%= f.label :email, class: 'block text-lime-200 font-semibold mb-2' %>
<%= f.email_field :email, autofocus: true, autocomplete: "email", class: 'block w-full px-4 py-2 border border-gray-700 rounded bg-gray-900 text-white focus:outline-none focus:border-lime-500' %>
</div>

<div class="actions">
<%= f.submit "Send me reset password instructions" %>
</div>
<% end %>
<div class="actions text-center">
<%= f.submit "Send me reset password instructions", class: 'bg-lime-500 hover:bg-lime-600 text-white font-bold py-2 px-4 rounded transition duration-300 ease-in-out focus:outline-none' %>
</div>
<% end %>

<%= render "devise/shared/links" %>
<div class="mt-4 text-center">
<%= render "devise/shared/links" %>
</div>
</div>
25 changes: 15 additions & 10 deletions app/views/devise/registrations/edit.html.erb
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
<h2 class="text-2xl font-bold mb-6 text-lime-200">Edit <%= resource_name.to_s.humanize %></h2>

<%= form_for(resource, as: resource_name, url: registration_path(resource_name), html: { method: :put, class: "space-y-6" }) do |f| %>
<%= devise_error_messages! %>
<%= render "devise/shared/error_messages", resource: resource %>

<div>
<%= f.label :email, class: 'block text-lime-200 font-semibold mb-2' %>
Expand All @@ -29,13 +29,16 @@
<%= f.text_field :avatar, class: 'block w-full px-4 py-2 border border-gray-700 rounded bg-gray-900 text-white focus:outline-none focus:border-lime-500' %>
</div>

<%= f.select :avatar_border, options_for_select([
['White', 'white'],
['Black', 'black'],
['None', 'none'],
['Rainbow', 'rainbow'],
['Rainbow Overlay', 'rainbow-overlay']
], @user.avatar_border), {}, class: 'block w-full px-4 py-2 border border-gray-700 rounded bg-gray-900 text-white focus:outline-none focus:border-lime-500' %>
<div>
<%= f.label :avatar_border, class: 'block text-lime-200 font-semibold mb-2' %>
<%= f.select :avatar_border, options_for_select([
['White', 'white'],
['Black', 'black'],
['None', 'none'],
['Rainbow', 'rainbow'],
['Rainbow Overlay', 'rainbow-overlay']
], @user.avatar_border), {}, class: 'block w-full px-4 py-2 border border-gray-700 rounded bg-gray-900 text-white focus:outline-none focus:border-lime-500' %>
</div>

<div>
<%= f.label :banner, class: 'block text-lime-200 font-semibold mb-2' %>
Expand Down Expand Up @@ -77,7 +80,7 @@
</div>

<div class="actions text-center mt-8">
<%= f.submit "Update", class: 'bg-lime-500 hover:bg-lime-600 text-white font-bold py-2 px-4 rounded-sm text-sm uppercase tracking-wide transition duration-300 ease-in-out focus:outline-none' %>
<%= f.submit "Update", class: 'bg-lime-500 hover:bg-lime-600 text-white font-bold py-2 px-4 rounded transition duration-300 ease-in-out focus:outline-none' %>
</div>
<% end %>

Expand All @@ -88,4 +91,6 @@
</div>
</div>

<%= link_to 'Back', user_links_path(username: current_user.username), class: 'text-white hover:text-lime-300' %>
<div class="mt-4 text-center">
<%= link_to 'Back', :back, class: 'text-lime-300 hover:text-lime-100 transition duration-300 ease-in-out' %>
</div>
Loading
Loading