Added Clients and Client Notes

This commit is contained in:
Adrian Hinz 2025-04-11 20:47:11 +02:00
parent eda4b52d5b
commit 49c74aeea3
30 changed files with 450 additions and 10 deletions

View File

@ -0,0 +1,48 @@
class ClientsController < ApplicationController
def index
@clients = Client.where(user_id: current_user.id)
end
def new
@client = Client.new
end
def create
@client = Client.new(client_params)
@client.user_id = current_user.id
if @client.save
redirect_to clients_path
else
render :new
end
end
def edit
@client = Client.find(params[:id])
end
def update
@client = Client.find(params[:id])
@client.user_id = current_user.id
if @client.update(client_params)
redirect_to clients_path
else
render 'edit'
end
end
def destroy
@client = Client.find(params[:id])
@client.destroy unless @client.blank?
redirect_to clients_path
end
private
def client_params
params.require(:client).permit(:name, :description)
end
end

View File

@ -0,0 +1,57 @@
class NotesController < ApplicationController
def index
@client = Client.where(id: params[:client_id]).first
@notes = Note.where(client_id: params[:client_id]).order(name: :asc)
end
def show
@note = Note.where('client_id = ? AND id = ?', params[:client_id], params[:id])
end
def new
@note = Note.new
@client = Client.where(id: params[:client_id]).first
end
def create
@note = Note.new(note_params)
@note.client_id = params[:client_id]
@client = Client.where(id: params[:client_id]).first
if @note.save
redirect_to notes_path(client_id: @client.id)
else
render :new
end
end
def edit
@note = Note.find(params[:id])
@client = Client.where(id: params[:client_id]).first
end
def update
@note = Note.find(params[:id])
@client = Client.where(id: params[:client_id]).first
if @note.update(note_params)
redirect_to notes_path(client_id: @client.id)
else
render 'edit'
end
end
def destroy
@note = Note.find(params[:id])
@client = Client.where(id: params[:client_id]).first
@note.destroy unless @note.blank?
redirect_to notes_path(client_id: @client.id)
end
private
def note_params
params.require(:note).permit(:name, :content)
end
end

View File

@ -7,6 +7,7 @@ module ApplicationHelper
ret += create_menu_li("glyphicon glyphicon-list-alt","Faktury","/invoices","invoices")
ret += create_menu_li("glyphicon glyphicon-book","Klienci","/customers","customers")
ret += create_menu_li("glyphicon glyphicon-shopping-cart","Produkty","/products","products")
ret += create_menu_li("glyphicon glyphicon-book","Obsługa","/clients","clients")
ret += create_menu_li("glyphicon glyphicon-cog","Ustawienia","/settings/index","settings")
return raw(ret)
end

3
app/models/client.rb Normal file
View File

@ -0,0 +1,3 @@
class Client < ApplicationRecord
belongs_to :user
end

View File

@ -0,0 +1,3 @@
class ClientFile < ApplicationRecord
belongs_to :client
end

3
app/models/note.rb Normal file
View File

@ -0,0 +1,3 @@
class Note < ApplicationRecord
belongs_to :client
end

3
app/models/platform.rb Normal file
View File

@ -0,0 +1,3 @@
class Platform < ApplicationRecord
belongs_to :client
end

View File

@ -0,0 +1,23 @@
<%= form_for @client, html: {class: "form-horizontal"} do |f| %>
<% if @client.errors.any? %>
<%= raw errors_to_html(@client.errors) %>
<% end %>
<div class="form-group">
<%= f.label :name, class: "col-sm-2 control-label" %>
<div class="col-sm-10">
<%= f.text_field :name, class: "form-control", placeholder: 'Nazwa' %>
</div>
</div>
<div class="form-group">
<%= f.label :description, class: "col-sm-2 control-label" %>
<div class="col-sm-10">
<%= f.text_area :description, class: "form-control" %>
</div>
</div>
<div class="form-group">
<div class="col-sm-offset-2 col-sm-10">
<%= f.submit 'Zapisz', class: "btn btn-primary" %>
</div>
</div>
<% end %>

View File

@ -0,0 +1,12 @@
<div class="col-lg-8 col-md-12 panel-default">
<div class="content-box-header panel-heading">
<div class="panel-title">Edycja klienta</div>
<div class="panel-options">
<%= link_to raw("<i class=\"glyphicon glyphicon-arrow-left text-success\"></i> " + I18n.t('back')), clients_path, title: I18n.t('back'), class: "text-primary" %>
</div>
</div>
<div class="content-box-large box-with-header">
<%= render 'form' %>
</div>
</div>
</div>

View File

@ -0,0 +1,29 @@
<div class="col-md-12 panel-default">
<div class="content-box-header panel-heading">
<div class="panel-title">Klienci - obsługa</div>
<div class="panel-options">
<%= link_to raw('<i class="glyphicon glyphicon-file text-success"></i> Nowy klient'), new_client_path, class: "text-primary" %><br/>
</div>
</div>
<div class="content-box-large box-with-header">
<table class="table table-striped table-bordered">
<tr>
<th>Nazwa</th>
<th>Opis</th>
<th>Akcje</th>
</tr>
<% @clients.each do |client| %>
<tr>
<td><%= link_to client.name, { controller: :notes, action: :index, client_id: client.id } %></td>
<td><%= client.description %></td>
<td>
<%= link_to raw('<i class="glyphicon glyphicon-pencil"></i> Edycja'), edit_client_path(client), class: "btn btn-primary btn-xs" %>
<%= link_to raw('<i class="glyphicon glyphicon-trash"></i> Usuń'), client_path(client), class: "btn btn-danger btn-xs", method: :delete, data: { confirm: 'Czy na pewno usunąć?' } %>
</td>
</tr>
<% end %>
</table>
</div>
</div>

View File

@ -0,0 +1,11 @@
<div class="col-lg-8 col-md-12 panel-default">
<div class="content-box-header panel-heading">
<div class="panel-title">Nowy klient</div>
<div class="panel-options">
<%= link_to raw("<i class=\"glyphicon glyphicon-arrow-left text-success\"></i> " + I18n.t('back')), clients_path, title: I18n.t('back'), class: "text-primary" %>
</div>
</div>
<div class="content-box-large box-with-header">
<%= render 'form' %>
</div>
</div>

View File

@ -22,13 +22,13 @@
</h1>
</div>
</div>
<div class="col-md-5"></div>
<div class="col-md-2">
<div class="col-md-3"></div>
<div class="col-md-4">
<div class="navbar navbar-inverse" role="banner">
<nav class="collapse navbar-collapse bs-navbar-collapse navbar-right" role="navigation">
<ul class="nav navbar-nav">
<li class="dropdown">
<a href="#" class="dropdown-toggle" data-toggle="dropdown">Moje konto
<a href="#" class="dropdown-toggle" data-toggle="dropdown">(<%= current_user.email %>) Moje konto
<b class="caret"></b>
</a>
<ul class="dropdown-menu animated fadeInUp">

View File

@ -0,0 +1,24 @@
<%= form_for @note, html: {class: "form-horizontal"} do |f| %>
<% if @note.errors.any? %>
<%= raw errors_to_html(@note.errors) %>
<% end %>
<%= hidden_field_tag :client_id, @client.id %>
<div class="form-group">
<%= f.label :name, class: "col-sm-2 control-label" %>
<div class="col-sm-10">
<%= f.text_field :name, class: "form-control", placeholder: 'Nazwa' %>
</div>
</div>
<div class="form-group">
<%= f.label :content, class: "col-sm-2 control-label" %>
<div class="col-sm-10">
<%= f.text_area :content, class: "form-control", rows: 20, style: 'font-family: monospace;' %>
</div>
</div>
<div class="form-group">
<div class="col-sm-offset-2 col-sm-10">
<%= f.submit 'Zapisz', class: "btn btn-primary" %>
</div>
</div>
<% end %>

View File

@ -0,0 +1,12 @@
<div class="col-lg-12 col-md-12 panel-default">
<div class="content-box-header panel-heading">
<div class="panel-title">Edycja notatki</div>
<div class="panel-options">
<%= link_to raw("<i class=\"glyphicon glyphicon-arrow-left text-success\"></i> " + I18n.t('back')), notes_path(client_id: @client.id), title: I18n.t('back'), class: "text-primary" %>
</div>
</div>
<div class="content-box-large box-with-header">
<%= render 'form' %>
</div>
</div>
</div>

View File

@ -0,0 +1,47 @@
<div class="col-md-12 panel-default">
<div class="content-box-header panel-heading">
<div class="panel-title">Klienci - notatki</div>
<div class="panel-options">
<%= link_to raw('<i class="glyphicon glyphicon-file text-success"></i> Nowa notatka'), new_note_path(client_id: @client.id), class: "text-primary" %><br/>
</div>
</div>
<div class="content-box-large box-with-header">
<table class="table table-striped table-bordered" style="table-layout: fixed; width: 100%;">
<tr>
<th style="width: 20%;">Nazwa</th>
<th style="width: calc(80% - 150px); ">Zawartość</th>
<th style="width: 150px;">Akcje</th>
</tr>
<% @notes.each do |note| %>
<tr>
<td><%= note.name %></td>
<td>
<% short_content = truncate(note.content, length: 30, separator: ' ', omission: '...') %>
<div style="max-width: 100%; overflow-x: auto; font-family: monospace; background: #f9f9f9; border: 1px solid #ddd; border-radius: 5px; padding: 8px; box-shadow: inset 0 1px 3px rgba(0,0,0,0.1);">
<% if note.content.length > 30 %>
<a href="#" onclick="event.preventDefault(); this.nextElementSibling.style.display = 'block'; this.style.display = 'none';">
<div style="white-space: nowrap;"><%= raw simple_format(short_content) %></div>
</a>
<div style="display: none; margin-top: 5px; white-space: nowrap;">
<%= raw simple_format(note.content) %>
</div>
<% else %>
<div style="white-space: nowrap;"><%= raw simple_format(short_content) %></div>
<% end %>
</div>
</td>
<td>
<%= link_to raw('<i class="glyphicon glyphicon-pencil"></i> Edycja'), edit_note_path(note, client_id: @client.id), class: "btn btn-primary btn-xs" %>
<%= link_to raw('<i class="glyphicon glyphicon-trash"></i> Usuń'), note_path(note, client_id: @client.id), class: "btn btn-danger btn-xs", method: :delete, data: { confirm: 'Czy na pewno usunąć?' } %>
</td>
</tr>
<% end %>
</table>
</div>
</div>

View File

@ -0,0 +1,11 @@
<div class="col-lg-12 col-md-12 panel-default">
<div class="content-box-header panel-heading">
<div class="panel-title">Nowa notatka</div>
<div class="panel-options">
<%= link_to raw("<i class=\"glyphicon glyphicon-arrow-left text-success\"></i> " + I18n.t('back')), notes_path(client_id: @client.id), title: I18n.t('back'), class: "text-primary" %>
</div>
</div>
<div class="content-box-large box-with-header">
<%= render 'form' %>
</div>
</div>

View File

@ -6,6 +6,8 @@ Rails.application.routes.draw do
resources :products
resources :invoices
resources :customers
resources :clients
resources :notes
root 'welcome#index'
# For details on the DSL available within this file, see http://guides.rubyonrails.org/routing.html

View File

@ -0,0 +1,11 @@
class CreateClients < ActiveRecord::Migration[5.0]
def change
create_table :clients do |t|
t.string :name
t.text :description
t.integer :user_id
t.timestamps
end
end
end

View File

@ -0,0 +1,12 @@
class CreatePlatforms < ActiveRecord::Migration[5.0]
def change
create_table :platforms do |t|
t.string :name
t.string :url
t.text :login_info
t.references :client, foreign_key: true
t.timestamps
end
end
end

View File

@ -0,0 +1,10 @@
class CreateNotes < ActiveRecord::Migration[5.0]
def change
create_table :notes do |t|
t.text :content
t.references :client, foreign_key: true
t.timestamps
end
end
end

View File

@ -0,0 +1,11 @@
class CreateClientFiles < ActiveRecord::Migration[5.0]
def change
create_table :client_files do |t|
t.string :name
t.text :description
t.references :client, foreign_key: true
t.timestamps
end
end
end

View File

@ -10,7 +10,23 @@
#
# It's strongly recommended that you check this file into your version control system.
ActiveRecord::Schema.define(version: 20161004200042) do
ActiveRecord::Schema.define(version: 20250411171138) do
create_table "client_files", force: :cascade, options: "ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_polish_ci" do |t|
t.string "name"
t.text "description", limit: 65535
t.integer "client_id"
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
t.index ["client_id"], name: "index_client_files_on_client_id", using: :btree
end
create_table "clients", force: :cascade, options: "ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_polish_ci" do |t|
t.string "name"
t.text "description", limit: 65535
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
end
create_table "customers", force: :cascade, options: "ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_polish_ci" do |t|
t.string "name"
@ -27,9 +43,9 @@ ActiveRecord::Schema.define(version: 20161004200042) do
create_table "invoice_products", force: :cascade, options: "ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_polish_ci" do |t|
t.integer "invoice_id"
t.integer "product_id"
t.decimal "netto_price", precision: 18, scale: 2
t.decimal "qty", precision: 18, scale: 3
t.integer "product_id", null: false
t.decimal "netto_price", precision: 10, scale: 2, null: false
t.decimal "qty", precision: 10, scale: 3, null: false
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
t.index ["invoice_id"], name: "index_invoice_products_on_invoice_id", using: :btree
@ -50,6 +66,24 @@ ActiveRecord::Schema.define(version: 20161004200042) do
t.index ["user_id"], name: "index_invoices_on_user_id", using: :btree
end
create_table "notes", force: :cascade, options: "ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_polish_ci" do |t|
t.text "content", limit: 65535
t.integer "client_id"
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
t.index ["client_id"], name: "index_notes_on_client_id", using: :btree
end
create_table "platforms", force: :cascade, options: "ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_polish_ci" do |t|
t.string "name"
t.string "url"
t.text "login_info", limit: 65535
t.integer "client_id"
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
t.index ["client_id"], name: "index_platforms_on_client_id", using: :btree
end
create_table "products", force: :cascade, options: "ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_polish_ci" do |t|
t.string "name"
t.integer "vat_id"
@ -73,9 +107,9 @@ ActiveRecord::Schema.define(version: 20161004200042) do
t.string "bank_name"
t.string "bank_account"
t.boolean "main"
t.boolean "active"
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
t.boolean "active", default: true, null: false
t.datetime "created_at", null: false
t.datetime "updated_at", null: false
t.index ["user_id"], name: "index_user_firms_on_user_id", using: :btree
end
@ -104,12 +138,15 @@ ActiveRecord::Schema.define(version: 20161004200042) do
t.datetime "updated_at", null: false
end
add_foreign_key "client_files", "clients"
add_foreign_key "customers", "users"
add_foreign_key "invoice_products", "invoices"
add_foreign_key "invoice_products", "products"
add_foreign_key "invoices", "customers"
add_foreign_key "invoices", "user_firms"
add_foreign_key "invoices", "users"
add_foreign_key "notes", "clients"
add_foreign_key "platforms", "clients"
add_foreign_key "products", "users"
add_foreign_key "products", "vats"
add_foreign_key "user_firms", "users"

11
test/fixtures/client_files.yml vendored Normal file
View File

@ -0,0 +1,11 @@
# Read about fixtures at http://api.rubyonrails.org/classes/ActiveRecord/FixtureSet.html
one:
name: MyString
description: MyText
client: one
two:
name: MyString
description: MyText
client: two

9
test/fixtures/clients.yml vendored Normal file
View File

@ -0,0 +1,9 @@
# Read about fixtures at http://api.rubyonrails.org/classes/ActiveRecord/FixtureSet.html
one:
name: MyString
description: MyText
two:
name: MyString
description: MyText

9
test/fixtures/notes.yml vendored Normal file
View File

@ -0,0 +1,9 @@
# Read about fixtures at http://api.rubyonrails.org/classes/ActiveRecord/FixtureSet.html
one:
content: MyText
client: one
two:
content: MyText
client: two

13
test/fixtures/platforms.yml vendored Normal file
View File

@ -0,0 +1,13 @@
# Read about fixtures at http://api.rubyonrails.org/classes/ActiveRecord/FixtureSet.html
one:
name: MyString
url: MyString
login_info: MyText
client: one
two:
name: MyString
url: MyString
login_info: MyText
client: two

View File

@ -0,0 +1,7 @@
require 'test_helper'
class ClientFileTest < ActiveSupport::TestCase
# test "the truth" do
# assert true
# end
end

View File

@ -0,0 +1,7 @@
require 'test_helper'
class ClientTest < ActiveSupport::TestCase
# test "the truth" do
# assert true
# end
end

7
test/models/note_test.rb Normal file
View File

@ -0,0 +1,7 @@
require 'test_helper'
class NoteTest < ActiveSupport::TestCase
# test "the truth" do
# assert true
# end
end

View File

@ -0,0 +1,7 @@
require 'test_helper'
class PlatformTest < ActiveSupport::TestCase
# test "the truth" do
# assert true
# end
end