Add IBAN and BIC fields to contacts
These two fields are just for information purposes, as Numerus does not have any way to wire transfer using these, but people might want to keep these in the contact’s info as a convenience. Since not every contact should have an IBAN, e.g., customers, and inside SEPA (European Union and some more countries) the BIC is not required, they are in two different relations in order to be optional without using NULL. For the IBAN i found an already made PostgreSQL module, but for BIC i had to write a regular expression based on the information i gathered from Wikipedia, because the ISO standard is not free. These two parameters for the add_contact and edit_contact functions are TEXT because i realized that these functions are intended to be used from the web application, that only deals with texts, so the ValueOrNil() function was unnecessarily complex and PostreSQL’s functions were better suited to “convert” from TEXT to IBAN or BIC. The same is true for EMAIL and URI domains, so i changed their parameter types to TEXT too. Closes #54.
This commit is contained in:
parent
1c0f126c58
commit
20827b2cfb
|
@ -17,7 +17,8 @@ Build-Depends:
|
|||
postgresql-15-pg-libphonenumber,
|
||||
postgresql-15-pgtap,
|
||||
postgresql-15-pguri,
|
||||
postgresql-15-vat
|
||||
postgresql-15-vat,
|
||||
postgresql-15-iban
|
||||
Standards-Version: 4.6.0
|
||||
XS-Go-Import-Path: dev.tandem.ws/tandem/numerus
|
||||
Vcs-Browser: https://dev.tandem.ws/tandem/numerus
|
||||
|
@ -55,6 +56,7 @@ Depends:
|
|||
postgresql-15-pg-libphonenumber,
|
||||
postgresql-15-pguri,
|
||||
postgresql-15-vat,
|
||||
postgresql-15-iban,
|
||||
sqitch
|
||||
Description: Simple invoicing and accounting web application
|
||||
A simple web application to keep invoice and accouting records, intended for
|
||||
|
|
|
@ -8,12 +8,17 @@
|
|||
-- requires: contact
|
||||
-- requires: tag_name
|
||||
-- requires: tax_details
|
||||
-- requires: contact_web
|
||||
-- requires: contact_phone
|
||||
-- requires: contact_tax_details
|
||||
-- requires: contact_iban
|
||||
-- requires: contact_bic
|
||||
|
||||
begin;
|
||||
|
||||
set search_path to numerus, public;
|
||||
|
||||
create or replace function add_contact(company_id integer, name text, phone text, email email, web uri, tax_details tax_details, tags tag_name[]) returns uuid as
|
||||
create or replace function add_contact(company_id integer, name text, phone text, email text, web text, tax_details tax_details, iban text, bic text, tags tag_name[]) returns uuid as
|
||||
$$
|
||||
declare
|
||||
cid integer;
|
||||
|
@ -43,21 +48,34 @@ begin
|
|||
;
|
||||
end if;
|
||||
|
||||
if web is not null and web <> '' then
|
||||
if web is not null and trim(web) <> '' then
|
||||
insert into contact_web (contact_id, uri)
|
||||
values (cid, add_contact.web)
|
||||
;
|
||||
end if;
|
||||
|
||||
if iban is not null and trim(iban) <> '' then
|
||||
insert into contact_iban (contact_id, iban)
|
||||
values (cid, add_contact.iban)
|
||||
;
|
||||
end if;
|
||||
|
||||
if bic is not null and trim(bic) <> '' then
|
||||
insert into contact_swift (contact_id, bic)
|
||||
values (cid, add_contact.bic)
|
||||
;
|
||||
end if;
|
||||
|
||||
|
||||
return cslug;
|
||||
end
|
||||
$$
|
||||
language plpgsql
|
||||
;
|
||||
|
||||
revoke execute on function add_contact(integer, text, text, email, uri, tax_details, tag_name[]) from public;
|
||||
grant execute on function add_contact(integer, text, text, email, uri, tax_details, tag_name[]) to invoicer;
|
||||
grant execute on function add_contact(integer, text, text, email, uri, tax_details, tag_name[]) to admin;
|
||||
revoke execute on function add_contact(integer, text, text, text, text, tax_details, text, text, tag_name[]) from public;
|
||||
grant execute on function add_contact(integer, text, text, text, text, tax_details, text, text, tag_name[]) to invoicer;
|
||||
grant execute on function add_contact(integer, text, text, text, text, tax_details, text, text, tag_name[]) to admin;
|
||||
|
||||
drop function if exists add_contact(integer, text, text, text, text, email, uri, text, text, text, text, country_code, tag_name[]);
|
||||
|
||||
|
|
|
@ -0,0 +1,14 @@
|
|||
-- Deploy numerus:bic to pg
|
||||
-- requires: schema_numerus
|
||||
|
||||
begin;
|
||||
|
||||
set search_path to numerus, public;
|
||||
|
||||
create domain bic as text
|
||||
check ( value ~ '^[A-Z]{6}[A-Z0-9]{2}([A-Z0-9]{3})?$' )
|
||||
;
|
||||
|
||||
comment on domain bic is 'A valid, but not necessarily existent, Business Identifier Code (ISO 9362)';
|
||||
|
||||
commit;
|
|
@ -0,0 +1,31 @@
|
|||
-- Deploy numerus:contact_iban to pg
|
||||
-- requires: schema_numerus
|
||||
-- requires: roles
|
||||
-- requires: contact
|
||||
-- requires: extension_iban
|
||||
|
||||
begin;
|
||||
|
||||
set search_path to numerus, public;
|
||||
|
||||
create table contact_iban (
|
||||
contact_id integer primary key references contact,
|
||||
iban iban not null
|
||||
);
|
||||
|
||||
grant select, insert, update, delete on table contact_iban to invoicer;
|
||||
grant select, insert, update, delete on table contact_iban to admin;
|
||||
|
||||
alter table contact_iban enable row level security;
|
||||
|
||||
create policy company_policy
|
||||
on contact_iban
|
||||
using (
|
||||
exists(
|
||||
select 1
|
||||
from contact
|
||||
where contact.contact_id = contact_iban.contact_id
|
||||
)
|
||||
);
|
||||
|
||||
commit;
|
|
@ -0,0 +1,31 @@
|
|||
-- Deploy numerus:contact_swift to pg
|
||||
-- requires: schema_numerus
|
||||
-- requires: roles
|
||||
-- requires: contact
|
||||
-- requires: bic
|
||||
|
||||
begin;
|
||||
|
||||
set search_path to numerus, public;
|
||||
|
||||
create table contact_swift (
|
||||
contact_id integer primary key references contact,
|
||||
bic bic not null
|
||||
);
|
||||
|
||||
grant select, insert, update, delete on table contact_swift to invoicer;
|
||||
grant select, insert, update, delete on table contact_swift to admin;
|
||||
|
||||
alter table contact_swift enable row level security;
|
||||
|
||||
create policy company_policy
|
||||
on contact_swift
|
||||
using (
|
||||
exists(
|
||||
select 1
|
||||
from contact
|
||||
where contact.contact_id = contact_swift.contact_id
|
||||
)
|
||||
);
|
||||
|
||||
commit;
|
|
@ -8,12 +8,17 @@
|
|||
-- requires: extension_vat
|
||||
-- requires: extension_pg_libphonenumber
|
||||
-- requires: tax_details
|
||||
-- requires: contact_web
|
||||
-- requires: contact_phone
|
||||
-- requires: contact_tax_details
|
||||
-- requires: contact_iban
|
||||
-- requires: contact_bic
|
||||
|
||||
begin;
|
||||
|
||||
set search_path to numerus, public;
|
||||
|
||||
create or replace function edit_contact(contact_slug uuid, name text, phone text, email email, web uri, tax_details tax_details, tags tag_name[]) returns uuid as
|
||||
create or replace function edit_contact(contact_slug uuid, name text, phone text, email text, web text, tax_details tax_details, iban text, bic text, tags tag_name[]) returns uuid as
|
||||
$$
|
||||
declare
|
||||
cid integer;
|
||||
|
@ -74,7 +79,7 @@ begin
|
|||
;
|
||||
end if;
|
||||
|
||||
if web is null or web = '' then
|
||||
if web is null or trim(web) = '' then
|
||||
delete from contact_web
|
||||
where contact_id = cid
|
||||
;
|
||||
|
@ -86,15 +91,39 @@ begin
|
|||
;
|
||||
end if;
|
||||
|
||||
if iban is null or trim(iban) = '' then
|
||||
delete from contact_iban
|
||||
where contact_id = cid
|
||||
;
|
||||
else
|
||||
insert into contact_iban (contact_id, iban)
|
||||
values (cid, edit_contact.iban)
|
||||
on conflict (contact_id) do update
|
||||
set iban = excluded.iban
|
||||
;
|
||||
end if;
|
||||
|
||||
if bic is null or trim(bic) = '' then
|
||||
delete from contact_swift
|
||||
where contact_id = cid
|
||||
;
|
||||
else
|
||||
insert into contact_swift (contact_id, bic)
|
||||
values (cid, edit_contact.bic)
|
||||
on conflict (contact_id) do update
|
||||
set bic = excluded.bic
|
||||
;
|
||||
end if;
|
||||
|
||||
return contact_slug;
|
||||
end
|
||||
$$
|
||||
language plpgsql
|
||||
;
|
||||
|
||||
revoke execute on function edit_contact(uuid, text, text, email, uri, tax_details, tag_name[]) from public;
|
||||
grant execute on function edit_contact(uuid, text, text, email, uri, tax_details, tag_name[]) to invoicer;
|
||||
grant execute on function edit_contact(uuid, text, text, email, uri, tax_details, tag_name[]) to admin;
|
||||
revoke execute on function edit_contact(uuid, text, text, text, text, tax_details, text, text, tag_name[]) from public;
|
||||
grant execute on function edit_contact(uuid, text, text, text, text, tax_details, text, text, tag_name[]) to invoicer;
|
||||
grant execute on function edit_contact(uuid, text, text, text, text, tax_details, text, text, tag_name[]) to admin;
|
||||
|
||||
|
||||
drop function if exists edit_contact(uuid, text, text, text, text, email, uri, text, text, text, text, country_code, tag_name[]);
|
||||
|
|
|
@ -0,0 +1,8 @@
|
|||
-- Deploy numerus:extension_iban to pg
|
||||
-- requires: schema_numerus
|
||||
|
||||
begin;
|
||||
|
||||
create extension if not exists iban;
|
||||
|
||||
commit;
|
|
@ -95,7 +95,7 @@ func HandleAddContact(w http.ResponseWriter, r *http.Request, _ httprouter.Param
|
|||
return
|
||||
}
|
||||
company := mustGetCompany(r)
|
||||
conn.MustExec(r.Context(), "select add_contact($1, $2, $3, $4, $5, $6, $7)", company.Id, form.Name, form.Phone.ValueOrNil(), form.Email.ValueOrNil(), form.Web.ValueOrNil(), form.TaxDetails(), form.Tags)
|
||||
conn.MustExec(r.Context(), "select add_contact($1, $2, $3, $4, $5, $6, $7, $8, $9)", company.Id, form.Name, form.Phone, form.Email, form.Web, form.TaxDetails(), form.IBAN, form.BIC, form.Tags)
|
||||
htmxRedirect(w, r, companyURI(company, "/contacts"))
|
||||
}
|
||||
|
||||
|
@ -115,7 +115,7 @@ func HandleUpdateContact(w http.ResponseWriter, r *http.Request, params httprout
|
|||
mustRenderEditContactForm(w, r, params[0].Value, form)
|
||||
return
|
||||
}
|
||||
slug := conn.MustGetText(r.Context(), "", "select edit_contact($1, $2, $3, $4, $5, $6, $7)", params[0].Value, form.Name, form.Phone.ValueOrNil(), form.Email.ValueOrNil(), form.Web.ValueOrNil(), form.TaxDetails(), form.Tags)
|
||||
slug := conn.MustGetText(r.Context(), "", "select edit_contact($1, $2, $3, $4, $5, $6, $7, $8, $9)", params[0].Value, form.Name, form.Phone, form.Email, form.Web, form.TaxDetails(), form.IBAN, form.BIC, form.Tags)
|
||||
if slug == "" {
|
||||
http.NotFound(w, r)
|
||||
}
|
||||
|
@ -230,6 +230,8 @@ type contactForm struct {
|
|||
Province *InputField
|
||||
PostalCode *InputField
|
||||
Country *SelectField
|
||||
IBAN *InputField
|
||||
BIC *InputField
|
||||
Tags *TagsField
|
||||
}
|
||||
|
||||
|
@ -326,6 +328,16 @@ func newContactForm(ctx context.Context, conn *Conn, locale *Locale) *contactFor
|
|||
`autocomplete="country"`,
|
||||
},
|
||||
},
|
||||
IBAN: &InputField{
|
||||
Name: "iban",
|
||||
Label: pgettext("input", "IBAN", locale),
|
||||
Type: "text",
|
||||
},
|
||||
BIC: &InputField{
|
||||
Name: "bic",
|
||||
Label: pgettext("bic", "BIC", locale),
|
||||
Type: "text",
|
||||
},
|
||||
Tags: &TagsField{
|
||||
Name: "tags",
|
||||
Label: pgettext("input", "Tags", locale),
|
||||
|
@ -349,6 +361,8 @@ func (form *contactForm) Parse(r *http.Request) error {
|
|||
form.Province.FillValue(r)
|
||||
form.PostalCode.FillValue(r)
|
||||
form.Country.FillValue(r)
|
||||
form.IBAN.FillValue(r)
|
||||
form.BIC.FillValue(r)
|
||||
form.Tags.FillValue(r)
|
||||
return nil
|
||||
}
|
||||
|
@ -387,6 +401,12 @@ func (form *contactForm) Validate(ctx context.Context, conn *Conn) bool {
|
|||
if form.Web.Val != "" {
|
||||
validator.CheckValidURL(form.Web, gettext("This value is not a valid web address. It should be like https://domain.com/.", form.locale))
|
||||
}
|
||||
if form.IBAN.Val != "" {
|
||||
validator.CheckValidIBANInput(form.IBAN, gettext("This values is not a valid IBAN.", form.locale))
|
||||
}
|
||||
if form.BIC.Val != "" {
|
||||
validator.CheckValidBICInput(form.IBAN, gettext("This values is not a valid BIC.", form.locale))
|
||||
}
|
||||
|
||||
return validator.AllOK()
|
||||
}
|
||||
|
@ -405,11 +425,15 @@ func (form *contactForm) MustFillFromDatabase(ctx context.Context, conn *Conn, s
|
|||
, province
|
||||
, postal_code
|
||||
, country_code
|
||||
, iban
|
||||
, bic
|
||||
, tags
|
||||
from contact
|
||||
left join contact_email using (contact_id)
|
||||
left join contact_phone using (contact_id)
|
||||
left join contact_web using (contact_id)
|
||||
left join contact_iban using (contact_id)
|
||||
left join contact_swift using (contact_id)
|
||||
left join contact_tax_details using (contact_id)
|
||||
where slug = $1
|
||||
`, slug).Scan(
|
||||
|
@ -425,6 +449,8 @@ func (form *contactForm) MustFillFromDatabase(ctx context.Context, conn *Conn, s
|
|||
form.Province,
|
||||
form.PostalCode,
|
||||
form.Country,
|
||||
form.IBAN,
|
||||
form.BIC,
|
||||
form.Tags))
|
||||
}
|
||||
|
||||
|
|
17
pkg/form.go
17
pkg/form.go
|
@ -59,13 +59,6 @@ func (field *InputField) Value() (driver.Value, error) {
|
|||
return field.Val, nil
|
||||
}
|
||||
|
||||
func (field *InputField) ValueOrNil() driver.Valuer {
|
||||
if field.Val == "" {
|
||||
return nil
|
||||
}
|
||||
return field
|
||||
}
|
||||
|
||||
func (field *InputField) FillValue(r *http.Request) {
|
||||
field.Val = strings.TrimSpace(r.FormValue(field.Name))
|
||||
}
|
||||
|
@ -457,6 +450,16 @@ func (v *FormValidator) CheckValidPhoneInput(field *InputField, country string,
|
|||
return v.checkInput(field, true, message)
|
||||
}
|
||||
|
||||
func (v *FormValidator) CheckValidIBANInput(field *InputField, message string) bool {
|
||||
// TODO: actual IBAN validation
|
||||
return v.checkInput(field, true, message)
|
||||
}
|
||||
|
||||
func (v *FormValidator) CheckValidBICInput(field *InputField, message string) bool {
|
||||
// TODO: actual BIC validation
|
||||
return v.checkInput(field, true, message)
|
||||
}
|
||||
|
||||
func (v *FormValidator) CheckPasswordConfirmation(password *InputField, confirm *InputField, message string) bool {
|
||||
return v.checkInput(confirm, password.Val == confirm.Val, message)
|
||||
}
|
||||
|
|
78
po/ca.po
78
po/ca.po
|
@ -8,7 +8,7 @@ msgid ""
|
|||
msgstr ""
|
||||
"Project-Id-Version: numerus\n"
|
||||
"Report-Msgid-Bugs-To: jordi@tandem.blog\n"
|
||||
"POT-Creation-Date: 2023-06-30 21:08+0200\n"
|
||||
"POT-Creation-Date: 2023-07-02 01:58+0200\n"
|
||||
"PO-Revision-Date: 2023-01-18 17:08+0100\n"
|
||||
"Last-Translator: jordi fita mas <jordi@tandem.blog>\n"
|
||||
"Language-Team: Catalan <ca@dodds.net>\n"
|
||||
|
@ -116,7 +116,7 @@ msgstr "Actualitza"
|
|||
|
||||
#: web/template/invoices/new.gohtml:90 web/template/invoices/edit.gohtml:91
|
||||
#: web/template/quotes/new.gohtml:91 web/template/quotes/edit.gohtml:92
|
||||
#: web/template/contacts/new.gohtml:44 web/template/contacts/edit.gohtml:48
|
||||
#: web/template/contacts/new.gohtml:49 web/template/contacts/edit.gohtml:53
|
||||
#: web/template/expenses/new.gohtml:33 web/template/expenses/edit.gohtml:38
|
||||
#: web/template/products/new.gohtml:30 web/template/products/edit.gohtml:36
|
||||
msgctxt "action"
|
||||
|
@ -648,7 +648,7 @@ msgctxt "title"
|
|||
msgid "Edit Product “%s”"
|
||||
msgstr "Edició del producte «%s»"
|
||||
|
||||
#: pkg/login.go:37 pkg/company.go:127 pkg/profile.go:40 pkg/contacts.go:255
|
||||
#: pkg/login.go:37 pkg/company.go:127 pkg/profile.go:40 pkg/contacts.go:257
|
||||
msgctxt "input"
|
||||
msgid "Email"
|
||||
msgstr "Correu-e"
|
||||
|
@ -662,7 +662,7 @@ msgstr "Contrasenya"
|
|||
msgid "Email can not be empty."
|
||||
msgstr "No podeu deixar el correu-e en blanc."
|
||||
|
||||
#: pkg/login.go:71 pkg/company.go:284 pkg/profile.go:90 pkg/contacts.go:385
|
||||
#: pkg/login.go:71 pkg/company.go:284 pkg/profile.go:90 pkg/contacts.go:399
|
||||
msgid "This value is not a valid email. It should be like name@domain.com."
|
||||
msgstr "Aquest valor no és un correu-e vàlid. Hauria de ser similar a nom@domini.cat."
|
||||
|
||||
|
@ -675,7 +675,7 @@ msgid "Invalid user or password."
|
|||
msgstr "Nom d’usuari o contrasenya incorrectes."
|
||||
|
||||
#: pkg/products.go:164 pkg/products.go:263 pkg/quote.go:823 pkg/invoices.go:909
|
||||
#: pkg/contacts.go:135 pkg/contacts.go:241
|
||||
#: pkg/contacts.go:135 pkg/contacts.go:243
|
||||
msgctxt "input"
|
||||
msgid "Name"
|
||||
msgstr "Nom"
|
||||
|
@ -683,7 +683,7 @@ msgstr "Nom"
|
|||
#: pkg/products.go:169 pkg/products.go:290 pkg/quote.go:174 pkg/quote.go:630
|
||||
#: pkg/expenses.go:188 pkg/expenses.go:347 pkg/invoices.go:174
|
||||
#: pkg/invoices.go:657 pkg/invoices.go:1208 pkg/contacts.go:140
|
||||
#: pkg/contacts.go:331
|
||||
#: pkg/contacts.go:343
|
||||
msgctxt "input"
|
||||
msgid "Tags"
|
||||
msgstr "Etiquetes"
|
||||
|
@ -732,7 +732,7 @@ msgid "Taxes"
|
|||
msgstr "Imposts"
|
||||
|
||||
#: pkg/products.go:309 pkg/quote.go:919 pkg/profile.go:92 pkg/invoices.go:1005
|
||||
#: pkg/contacts.go:378
|
||||
#: pkg/contacts.go:392
|
||||
msgid "Name can not be empty."
|
||||
msgstr "No podeu deixar el nom en blanc."
|
||||
|
||||
|
@ -759,47 +759,47 @@ msgctxt "input"
|
|||
msgid "Trade name"
|
||||
msgstr "Nom comercial"
|
||||
|
||||
#: pkg/company.go:118 pkg/contacts.go:247
|
||||
#: pkg/company.go:118 pkg/contacts.go:249
|
||||
msgctxt "input"
|
||||
msgid "Phone"
|
||||
msgstr "Telèfon"
|
||||
|
||||
#: pkg/company.go:136 pkg/contacts.go:263
|
||||
#: pkg/company.go:136 pkg/contacts.go:265
|
||||
msgctxt "input"
|
||||
msgid "Web"
|
||||
msgstr "Web"
|
||||
|
||||
#: pkg/company.go:144 pkg/contacts.go:275
|
||||
#: pkg/company.go:144 pkg/contacts.go:277
|
||||
msgctxt "input"
|
||||
msgid "Business name"
|
||||
msgstr "Nom i cognoms"
|
||||
|
||||
#: pkg/company.go:154 pkg/contacts.go:285
|
||||
#: pkg/company.go:154 pkg/contacts.go:287
|
||||
msgctxt "input"
|
||||
msgid "VAT number"
|
||||
msgstr "DNI / NIF"
|
||||
|
||||
#: pkg/company.go:160 pkg/contacts.go:291
|
||||
#: pkg/company.go:160 pkg/contacts.go:293
|
||||
msgctxt "input"
|
||||
msgid "Address"
|
||||
msgstr "Adreça"
|
||||
|
||||
#: pkg/company.go:169 pkg/contacts.go:300
|
||||
#: pkg/company.go:169 pkg/contacts.go:302
|
||||
msgctxt "input"
|
||||
msgid "City"
|
||||
msgstr "Població"
|
||||
|
||||
#: pkg/company.go:175 pkg/contacts.go:306
|
||||
#: pkg/company.go:175 pkg/contacts.go:308
|
||||
msgctxt "input"
|
||||
msgid "Province"
|
||||
msgstr "Província"
|
||||
|
||||
#: pkg/company.go:181 pkg/contacts.go:312
|
||||
#: pkg/company.go:181 pkg/contacts.go:314
|
||||
msgctxt "input"
|
||||
msgid "Postal code"
|
||||
msgstr "Codi postal"
|
||||
|
||||
#: pkg/company.go:190 pkg/contacts.go:321
|
||||
#: pkg/company.go:190 pkg/contacts.go:323
|
||||
msgctxt "input"
|
||||
msgid "Country"
|
||||
msgstr "País"
|
||||
|
@ -834,23 +834,23 @@ msgctxt "input"
|
|||
msgid "Legal disclaimer"
|
||||
msgstr "Nota legal"
|
||||
|
||||
#: pkg/company.go:271 pkg/contacts.go:361
|
||||
#: pkg/company.go:271 pkg/contacts.go:375
|
||||
msgid "Selected country is not valid."
|
||||
msgstr "Heu seleccionat un país que no és vàlid."
|
||||
|
||||
#: pkg/company.go:275 pkg/contacts.go:364
|
||||
#: pkg/company.go:275 pkg/contacts.go:378
|
||||
msgid "Business name can not be empty."
|
||||
msgstr "No podeu deixar el nom i els cognoms en blanc."
|
||||
|
||||
#: pkg/company.go:276 pkg/contacts.go:365
|
||||
#: pkg/company.go:276 pkg/contacts.go:379
|
||||
msgid "Business name must have at least two letters."
|
||||
msgstr "Nom i cognoms han de tenir com a mínim dues lletres."
|
||||
|
||||
#: pkg/company.go:277 pkg/contacts.go:366
|
||||
#: pkg/company.go:277 pkg/contacts.go:380
|
||||
msgid "VAT number can not be empty."
|
||||
msgstr "No podeu deixar el DNI o NIF en blanc."
|
||||
|
||||
#: pkg/company.go:278 pkg/contacts.go:367
|
||||
#: pkg/company.go:278 pkg/contacts.go:381
|
||||
msgid "This value is not a valid VAT number."
|
||||
msgstr "Aquest valor no és un DNI o NIF vàlid."
|
||||
|
||||
|
@ -858,31 +858,31 @@ msgstr "Aquest valor no és un DNI o NIF vàlid."
|
|||
msgid "Phone can not be empty."
|
||||
msgstr "No podeu deixar el telèfon en blanc."
|
||||
|
||||
#: pkg/company.go:281 pkg/contacts.go:382
|
||||
#: pkg/company.go:281 pkg/contacts.go:396
|
||||
msgid "This value is not a valid phone number."
|
||||
msgstr "Aquest valor no és un telèfon vàlid."
|
||||
|
||||
#: pkg/company.go:287 pkg/contacts.go:388
|
||||
#: pkg/company.go:287 pkg/contacts.go:402
|
||||
msgid "This value is not a valid web address. It should be like https://domain.com/."
|
||||
msgstr "Aquest valor no és una adreça web vàlida. Hauria de ser similar a https://domini.cat/."
|
||||
|
||||
#: pkg/company.go:289 pkg/contacts.go:369
|
||||
#: pkg/company.go:289 pkg/contacts.go:383
|
||||
msgid "Address can not be empty."
|
||||
msgstr "No podeu deixar l’adreça en blanc."
|
||||
|
||||
#: pkg/company.go:290 pkg/contacts.go:370
|
||||
#: pkg/company.go:290 pkg/contacts.go:384
|
||||
msgid "City can not be empty."
|
||||
msgstr "No podeu deixar la població en blanc."
|
||||
|
||||
#: pkg/company.go:291 pkg/contacts.go:371
|
||||
#: pkg/company.go:291 pkg/contacts.go:385
|
||||
msgid "Province can not be empty."
|
||||
msgstr "No podeu deixar la província en blanc."
|
||||
|
||||
#: pkg/company.go:292 pkg/contacts.go:373
|
||||
#: pkg/company.go:292 pkg/contacts.go:387
|
||||
msgid "Postal code can not be empty."
|
||||
msgstr "No podeu deixar el codi postal en blanc."
|
||||
|
||||
#: pkg/company.go:293 pkg/contacts.go:374
|
||||
#: pkg/company.go:293 pkg/contacts.go:388
|
||||
msgid "This value is not a valid postal code."
|
||||
msgstr "Aquest valor no és un codi postal vàlid."
|
||||
|
||||
|
@ -1248,15 +1248,33 @@ msgstr "DD/MM/YYYY"
|
|||
msgid "Invoice product ID must be a number greater than zero."
|
||||
msgstr "L’ID del producte de factura ha de ser un número major a zero."
|
||||
|
||||
#: pkg/contacts.go:271
|
||||
#: pkg/contacts.go:273
|
||||
msgctxt "input"
|
||||
msgid "Need to input tax details"
|
||||
msgstr "Necessito poder facturar aquest contacte"
|
||||
|
||||
#: pkg/contacts.go:379
|
||||
#: pkg/contacts.go:333
|
||||
msgctxt "input"
|
||||
msgid "IBAN"
|
||||
msgstr "IBAN"
|
||||
|
||||
#: pkg/contacts.go:338
|
||||
msgctxt "bic"
|
||||
msgid "BIC"
|
||||
msgstr "BIC"
|
||||
|
||||
#: pkg/contacts.go:393
|
||||
msgid "Name must have at least two letters."
|
||||
msgstr "El nom ha de tenir com a mínim dues lletres."
|
||||
|
||||
#: pkg/contacts.go:405
|
||||
msgid "This values is not a valid IBAN."
|
||||
msgstr "Aquest valor no és un IBAN vàlid."
|
||||
|
||||
#: pkg/contacts.go:408
|
||||
msgid "This values is not a valid BIC."
|
||||
msgstr "Aquest valor no és un BIC vàlid."
|
||||
|
||||
#~ msgctxt "action"
|
||||
#~ msgid "Update contact"
|
||||
#~ msgstr "Actualitza contacte"
|
||||
|
|
78
po/es.po
78
po/es.po
|
@ -7,7 +7,7 @@ msgid ""
|
|||
msgstr ""
|
||||
"Project-Id-Version: numerus\n"
|
||||
"Report-Msgid-Bugs-To: jordi@tandem.blog\n"
|
||||
"POT-Creation-Date: 2023-06-30 21:08+0200\n"
|
||||
"POT-Creation-Date: 2023-07-02 01:58+0200\n"
|
||||
"PO-Revision-Date: 2023-01-18 17:45+0100\n"
|
||||
"Last-Translator: jordi fita mas <jordi@tandem.blog>\n"
|
||||
"Language-Team: Spanish <es@tp.org.es>\n"
|
||||
|
@ -116,7 +116,7 @@ msgstr "Actualizar"
|
|||
|
||||
#: web/template/invoices/new.gohtml:90 web/template/invoices/edit.gohtml:91
|
||||
#: web/template/quotes/new.gohtml:91 web/template/quotes/edit.gohtml:92
|
||||
#: web/template/contacts/new.gohtml:44 web/template/contacts/edit.gohtml:48
|
||||
#: web/template/contacts/new.gohtml:49 web/template/contacts/edit.gohtml:53
|
||||
#: web/template/expenses/new.gohtml:33 web/template/expenses/edit.gohtml:38
|
||||
#: web/template/products/new.gohtml:30 web/template/products/edit.gohtml:36
|
||||
msgctxt "action"
|
||||
|
@ -648,7 +648,7 @@ msgctxt "title"
|
|||
msgid "Edit Product “%s”"
|
||||
msgstr "Edición del producto «%s»"
|
||||
|
||||
#: pkg/login.go:37 pkg/company.go:127 pkg/profile.go:40 pkg/contacts.go:255
|
||||
#: pkg/login.go:37 pkg/company.go:127 pkg/profile.go:40 pkg/contacts.go:257
|
||||
msgctxt "input"
|
||||
msgid "Email"
|
||||
msgstr "Correo-e"
|
||||
|
@ -662,7 +662,7 @@ msgstr "Contraseña"
|
|||
msgid "Email can not be empty."
|
||||
msgstr "No podéis dejar el correo-e en blanco."
|
||||
|
||||
#: pkg/login.go:71 pkg/company.go:284 pkg/profile.go:90 pkg/contacts.go:385
|
||||
#: pkg/login.go:71 pkg/company.go:284 pkg/profile.go:90 pkg/contacts.go:399
|
||||
msgid "This value is not a valid email. It should be like name@domain.com."
|
||||
msgstr "Este valor no es un correo-e válido. Tiene que ser parecido a nombre@dominio.es."
|
||||
|
||||
|
@ -675,7 +675,7 @@ msgid "Invalid user or password."
|
|||
msgstr "Nombre de usuario o contraseña inválido."
|
||||
|
||||
#: pkg/products.go:164 pkg/products.go:263 pkg/quote.go:823 pkg/invoices.go:909
|
||||
#: pkg/contacts.go:135 pkg/contacts.go:241
|
||||
#: pkg/contacts.go:135 pkg/contacts.go:243
|
||||
msgctxt "input"
|
||||
msgid "Name"
|
||||
msgstr "Nombre"
|
||||
|
@ -683,7 +683,7 @@ msgstr "Nombre"
|
|||
#: pkg/products.go:169 pkg/products.go:290 pkg/quote.go:174 pkg/quote.go:630
|
||||
#: pkg/expenses.go:188 pkg/expenses.go:347 pkg/invoices.go:174
|
||||
#: pkg/invoices.go:657 pkg/invoices.go:1208 pkg/contacts.go:140
|
||||
#: pkg/contacts.go:331
|
||||
#: pkg/contacts.go:343
|
||||
msgctxt "input"
|
||||
msgid "Tags"
|
||||
msgstr "Etiquetes"
|
||||
|
@ -732,7 +732,7 @@ msgid "Taxes"
|
|||
msgstr "Impuestos"
|
||||
|
||||
#: pkg/products.go:309 pkg/quote.go:919 pkg/profile.go:92 pkg/invoices.go:1005
|
||||
#: pkg/contacts.go:378
|
||||
#: pkg/contacts.go:392
|
||||
msgid "Name can not be empty."
|
||||
msgstr "No podéis dejar el nombre en blanco."
|
||||
|
||||
|
@ -759,47 +759,47 @@ msgctxt "input"
|
|||
msgid "Trade name"
|
||||
msgstr "Nombre comercial"
|
||||
|
||||
#: pkg/company.go:118 pkg/contacts.go:247
|
||||
#: pkg/company.go:118 pkg/contacts.go:249
|
||||
msgctxt "input"
|
||||
msgid "Phone"
|
||||
msgstr "Teléfono"
|
||||
|
||||
#: pkg/company.go:136 pkg/contacts.go:263
|
||||
#: pkg/company.go:136 pkg/contacts.go:265
|
||||
msgctxt "input"
|
||||
msgid "Web"
|
||||
msgstr "Web"
|
||||
|
||||
#: pkg/company.go:144 pkg/contacts.go:275
|
||||
#: pkg/company.go:144 pkg/contacts.go:277
|
||||
msgctxt "input"
|
||||
msgid "Business name"
|
||||
msgstr "Nombre y apellidos"
|
||||
|
||||
#: pkg/company.go:154 pkg/contacts.go:285
|
||||
#: pkg/company.go:154 pkg/contacts.go:287
|
||||
msgctxt "input"
|
||||
msgid "VAT number"
|
||||
msgstr "DNI / NIF"
|
||||
|
||||
#: pkg/company.go:160 pkg/contacts.go:291
|
||||
#: pkg/company.go:160 pkg/contacts.go:293
|
||||
msgctxt "input"
|
||||
msgid "Address"
|
||||
msgstr "Dirección"
|
||||
|
||||
#: pkg/company.go:169 pkg/contacts.go:300
|
||||
#: pkg/company.go:169 pkg/contacts.go:302
|
||||
msgctxt "input"
|
||||
msgid "City"
|
||||
msgstr "Población"
|
||||
|
||||
#: pkg/company.go:175 pkg/contacts.go:306
|
||||
#: pkg/company.go:175 pkg/contacts.go:308
|
||||
msgctxt "input"
|
||||
msgid "Province"
|
||||
msgstr "Provincia"
|
||||
|
||||
#: pkg/company.go:181 pkg/contacts.go:312
|
||||
#: pkg/company.go:181 pkg/contacts.go:314
|
||||
msgctxt "input"
|
||||
msgid "Postal code"
|
||||
msgstr "Código postal"
|
||||
|
||||
#: pkg/company.go:190 pkg/contacts.go:321
|
||||
#: pkg/company.go:190 pkg/contacts.go:323
|
||||
msgctxt "input"
|
||||
msgid "Country"
|
||||
msgstr "País"
|
||||
|
@ -834,23 +834,23 @@ msgctxt "input"
|
|||
msgid "Legal disclaimer"
|
||||
msgstr "Nota legal"
|
||||
|
||||
#: pkg/company.go:271 pkg/contacts.go:361
|
||||
#: pkg/company.go:271 pkg/contacts.go:375
|
||||
msgid "Selected country is not valid."
|
||||
msgstr "Habéis escogido un país que no es válido."
|
||||
|
||||
#: pkg/company.go:275 pkg/contacts.go:364
|
||||
#: pkg/company.go:275 pkg/contacts.go:378
|
||||
msgid "Business name can not be empty."
|
||||
msgstr "No podéis dejar el nombre y los apellidos en blanco."
|
||||
|
||||
#: pkg/company.go:276 pkg/contacts.go:365
|
||||
#: pkg/company.go:276 pkg/contacts.go:379
|
||||
msgid "Business name must have at least two letters."
|
||||
msgstr "El nombre y los apellidos deben contener como mínimo dos letras."
|
||||
|
||||
#: pkg/company.go:277 pkg/contacts.go:366
|
||||
#: pkg/company.go:277 pkg/contacts.go:380
|
||||
msgid "VAT number can not be empty."
|
||||
msgstr "No podéis dejar el DNI o NIF en blanco."
|
||||
|
||||
#: pkg/company.go:278 pkg/contacts.go:367
|
||||
#: pkg/company.go:278 pkg/contacts.go:381
|
||||
msgid "This value is not a valid VAT number."
|
||||
msgstr "Este valor no es un DNI o NIF válido."
|
||||
|
||||
|
@ -858,31 +858,31 @@ msgstr "Este valor no es un DNI o NIF válido."
|
|||
msgid "Phone can not be empty."
|
||||
msgstr "No podéis dejar el teléfono en blanco."
|
||||
|
||||
#: pkg/company.go:281 pkg/contacts.go:382
|
||||
#: pkg/company.go:281 pkg/contacts.go:396
|
||||
msgid "This value is not a valid phone number."
|
||||
msgstr "Este valor no es un teléfono válido."
|
||||
|
||||
#: pkg/company.go:287 pkg/contacts.go:388
|
||||
#: pkg/company.go:287 pkg/contacts.go:402
|
||||
msgid "This value is not a valid web address. It should be like https://domain.com/."
|
||||
msgstr "Este valor no es una dirección web válida. Tiene que ser parecida a https://dominio.es/."
|
||||
|
||||
#: pkg/company.go:289 pkg/contacts.go:369
|
||||
#: pkg/company.go:289 pkg/contacts.go:383
|
||||
msgid "Address can not be empty."
|
||||
msgstr "No podéis dejar la dirección en blanco."
|
||||
|
||||
#: pkg/company.go:290 pkg/contacts.go:370
|
||||
#: pkg/company.go:290 pkg/contacts.go:384
|
||||
msgid "City can not be empty."
|
||||
msgstr "No podéis dejar la población en blanco."
|
||||
|
||||
#: pkg/company.go:291 pkg/contacts.go:371
|
||||
#: pkg/company.go:291 pkg/contacts.go:385
|
||||
msgid "Province can not be empty."
|
||||
msgstr "No podéis dejar la provincia en blanco."
|
||||
|
||||
#: pkg/company.go:292 pkg/contacts.go:373
|
||||
#: pkg/company.go:292 pkg/contacts.go:387
|
||||
msgid "Postal code can not be empty."
|
||||
msgstr "No podéis dejar el código postal en blanco."
|
||||
|
||||
#: pkg/company.go:293 pkg/contacts.go:374
|
||||
#: pkg/company.go:293 pkg/contacts.go:388
|
||||
msgid "This value is not a valid postal code."
|
||||
msgstr "Este valor no es un código postal válido válido."
|
||||
|
||||
|
@ -1248,15 +1248,33 @@ msgstr "DD/MM/YYYY"
|
|||
msgid "Invoice product ID must be a number greater than zero."
|
||||
msgstr "El ID de producto de factura tiene que ser un número mayor a cero."
|
||||
|
||||
#: pkg/contacts.go:271
|
||||
#: pkg/contacts.go:273
|
||||
msgctxt "input"
|
||||
msgid "Need to input tax details"
|
||||
msgstr "Necesito facturar este contacto"
|
||||
|
||||
#: pkg/contacts.go:379
|
||||
#: pkg/contacts.go:333
|
||||
msgctxt "input"
|
||||
msgid "IBAN"
|
||||
msgstr "IBAN"
|
||||
|
||||
#: pkg/contacts.go:338
|
||||
msgctxt "bic"
|
||||
msgid "BIC"
|
||||
msgstr "BIC"
|
||||
|
||||
#: pkg/contacts.go:393
|
||||
msgid "Name must have at least two letters."
|
||||
msgstr "El nombre debe contener como mínimo dos letras."
|
||||
|
||||
#: pkg/contacts.go:405
|
||||
msgid "This values is not a valid IBAN."
|
||||
msgstr "Este valor no es un IBAN válido."
|
||||
|
||||
#: pkg/contacts.go:408
|
||||
msgid "This values is not a valid BIC."
|
||||
msgstr "Este valor no es un BIC válido."
|
||||
|
||||
#~ msgctxt "action"
|
||||
#~ msgid "Update contact"
|
||||
#~ msgstr "Actualizar contacto"
|
||||
|
|
|
@ -34,6 +34,6 @@ grant execute on function add_contact(integer, text, text, text, text, email, ur
|
|||
grant execute on function add_contact(integer, text, text, text, text, email, uri, text, text, text, text, country_code, tag_name[]) to admin;
|
||||
|
||||
|
||||
drop function if exists add_contact(integer, text, text, email, uri, tax_details, tag_name[]);
|
||||
drop function if exists add_contact(integer, text, text, text, text, tax_details, text, text, tag_name[]);
|
||||
|
||||
commit;
|
||||
|
|
|
@ -0,0 +1,7 @@
|
|||
-- Revert numerus:bic from pg
|
||||
|
||||
begin;
|
||||
|
||||
drop domain if exists numerus.bic;
|
||||
|
||||
commit;
|
|
@ -0,0 +1,7 @@
|
|||
-- Revert numerus:contact_iban from pg
|
||||
|
||||
begin;
|
||||
|
||||
drop table if exists numerus.contact_iban;
|
||||
|
||||
commit;
|
|
@ -0,0 +1,7 @@
|
|||
-- Revert numerus:contact_swift from pg
|
||||
|
||||
begin;
|
||||
|
||||
drop table if exists numerus.contact_swift;
|
||||
|
||||
commit;
|
|
@ -50,6 +50,6 @@ revoke execute on function edit_contact(uuid, text, text, text, text, email, uri
|
|||
grant execute on function edit_contact(uuid, text, text, text, text, email, uri, text, text, text, text, country_code, tag_name[]) to invoicer;
|
||||
grant execute on function edit_contact(uuid, text, text, text, text, email, uri, text, text, text, text, country_code, tag_name[]) to admin;
|
||||
|
||||
drop function if exists edit_contact(uuid, text, text, email, uri, tax_details, tag_name[]);
|
||||
drop function if exists edit_contact(uuid, text, text, text, text, tax_details, text, text, tag_name[]);
|
||||
|
||||
commit;
|
||||
|
|
|
@ -0,0 +1,7 @@
|
|||
-- Revert numerus:extension_iban from pg
|
||||
|
||||
begin;
|
||||
|
||||
drop extension if exists iban;
|
||||
|
||||
commit;
|
|
@ -104,6 +104,10 @@ contact_email [roles schema_numerus email contact] 2023-06-28T11:47:19Z jordi fi
|
|||
contact_web [roles schema_numerus extension_uri contact] 2023-06-28T12:01:07Z jordi fita mas <jordi@tandem.blog> # Add relation to keep contacts’ websites
|
||||
contact_tax_details [roles schema_numerus contact extension_vat country_code country] 2023-06-23T09:14:03Z jordi fita mas <jordi@tandem.blog> # Add relation of contact’s tax details
|
||||
tax_details [schema_numerus extension_vat country_code] 2023-06-29T10:57:57Z jordi fita mas <jordi@tandem.blog> # Add composite type for contacts’ tax details
|
||||
add_contact [add_contact@v0 tax_details] 2023-06-29T11:10:15Z jordi fita mas <jordi@tandem.blog> # Change add contact to accept a tax_detail parameter and use the new relations
|
||||
edit_contact [edit_contact@v0 tax_details] 2023-06-29T11:50:41Z jordi fita mas <jordi@tandem.blog> # Change edit_contact to require tax_details parameter and to use new relations for web, email, and phone
|
||||
invoice_contact_id_fkey [schema_numerus invoice contact_tax_details] 2023-06-30T16:50:45Z jordi fita mas <jordi@tandem.blog> # Update invoice’s contact_id foreign key to point to tax sales
|
||||
extension_iban [schema_numerus] 2023-07-01T22:20:38Z jordi fita mas <jordi@tandem.blog> # Add IBAN extension
|
||||
contact_iban [schema_numerus roles contact extension_iban] 2023-07-01T22:27:38Z jordi fita mas <jordi@tandem.blog> # Add relation for contact iban
|
||||
bic [schema_numerus] 2023-07-01T22:46:30Z jordi fita mas <jordi@tandem.blog> # Add BIC domain
|
||||
contact_swift [schema_numerus roles contact bic] 2023-07-01T23:03:13Z jordi fita mas <jordi@tandem.blog> # Add relation for contact’s SWIFT-BIC
|
||||
add_contact [add_contact@v0 tax_details contact_web contact_email contact_phone contact_iban contact_swift] 2023-06-29T11:10:15Z jordi fita mas <jordi@tandem.blog> # Change add contact to accept a tax_detail parameter and use the new relations for web, email, phone, iban, and swift
|
||||
edit_contact [edit_contact@v0 tax_details contact_web contact_email contact_phone contact_iban contact_swift] 2023-06-29T11:50:41Z jordi fita mas <jordi@tandem.blog> # Change edit_contact to require tax_details parameter and to use new relations for web, email, phone, iban, and swift
|
||||
|
|
|
@ -5,22 +5,28 @@ reset client_min_messages;
|
|||
|
||||
begin;
|
||||
|
||||
select plan(18);
|
||||
select plan(20);
|
||||
|
||||
set search_path to auth, numerus, public;
|
||||
|
||||
select has_function('numerus', 'add_contact', array ['integer', 'text', 'text', 'email', 'uri', 'tax_details', 'tag_name[]']);
|
||||
select function_lang_is('numerus', 'add_contact', array ['integer', 'text', 'text', 'email', 'uri', 'tax_details', 'tag_name[]'], 'plpgsql');
|
||||
select function_returns('numerus', 'add_contact', array ['integer', 'text', 'text', 'email', 'uri', 'tax_details', 'tag_name[]'], 'uuid');
|
||||
select isnt_definer('numerus', 'add_contact', array ['integer', 'text', 'text', 'email', 'uri', 'tax_details', 'tag_name[]']);
|
||||
select volatility_is('numerus', 'add_contact', array ['integer', 'text', 'text', 'email', 'uri', 'tax_details', 'tag_name[]'], 'volatile');
|
||||
select function_privs_are('numerus', 'add_contact', array ['integer', 'text', 'text', 'email', 'uri', 'tax_details', 'tag_name[]'], 'guest', array []::text[]);
|
||||
select function_privs_are('numerus', 'add_contact', array ['integer', 'text', 'text', 'email', 'uri', 'tax_details', 'tag_name[]'], 'invoicer', array ['EXECUTE']);
|
||||
select function_privs_are('numerus', 'add_contact', array ['integer', 'text', 'text', 'email', 'uri', 'tax_details', 'tag_name[]'], 'admin', array ['EXECUTE']);
|
||||
select function_privs_are('numerus', 'add_contact', array ['integer', 'text', 'text', 'email', 'uri', 'tax_details', 'tag_name[]'], 'authenticator', array []::text[]);
|
||||
select has_function('numerus', 'add_contact', array ['integer', 'text', 'text', 'text', 'text', 'tax_details', 'text', 'text', 'tag_name[]']);
|
||||
select function_lang_is('numerus', 'add_contact', array ['integer', 'text', 'text', 'text', 'text', 'tax_details', 'text', 'text', 'tag_name[]'], 'plpgsql');
|
||||
select function_returns('numerus', 'add_contact', array ['integer', 'text', 'text', 'text', 'text', 'tax_details', 'text', 'text', 'tag_name[]'], 'uuid');
|
||||
select isnt_definer('numerus', 'add_contact', array ['integer', 'text', 'text', 'text', 'text', 'tax_details', 'text', 'text', 'tag_name[]']);
|
||||
select volatility_is('numerus', 'add_contact', array ['integer', 'text', 'text', 'text', 'text', 'tax_details', 'text', 'text', 'tag_name[]'], 'volatile');
|
||||
select function_privs_are('numerus', 'add_contact', array ['integer', 'text', 'text', 'text', 'text', 'tax_details', 'text', 'text', 'tag_name[]'], 'guest', array []::text[]);
|
||||
select function_privs_are('numerus', 'add_contact', array ['integer', 'text', 'text', 'text', 'text', 'tax_details', 'text', 'text', 'tag_name[]'], 'invoicer', array ['EXECUTE']);
|
||||
select function_privs_are('numerus', 'add_contact', array ['integer', 'text', 'text', 'text', 'text', 'tax_details', 'text', 'text', 'tag_name[]'], 'admin', array ['EXECUTE']);
|
||||
select function_privs_are('numerus', 'add_contact', array ['integer', 'text', 'text', 'text', 'text', 'tax_details', 'text', 'text', 'tag_name[]'], 'authenticator', array []::text[]);
|
||||
|
||||
|
||||
set client_min_messages to warning;
|
||||
truncate contact_swift cascade;
|
||||
truncate contact_iban cascade;
|
||||
truncate contact_web cascade;
|
||||
truncate contact_email cascade;
|
||||
truncate contact_phone cascade;
|
||||
truncate contact_tax_details cascade;
|
||||
truncate contact cascade;
|
||||
truncate payment_method cascade;
|
||||
truncate company cascade;
|
||||
|
@ -41,22 +47,22 @@ values (111, 1, 'cash', 'cash')
|
|||
set constraints "company_default_payment_method_id_fkey" immediate;
|
||||
|
||||
select lives_ok(
|
||||
$$ select add_contact(1, 'Contact 2.1', '777-777-777', null, 'https://c', null, '{tag1,tag2}') $$,
|
||||
$$ select add_contact(1, 'Contact 2.1', '777-777-777', '', 'https://c', null, 'NL35INGB5262865534', '', '{tag1,tag2}') $$,
|
||||
'Should be able to insert a contact for the first company with two tags, no email, and no tax details'
|
||||
);
|
||||
|
||||
select lives_ok(
|
||||
$$ select add_contact(1, 'Contact 2.2', null, 'd@d', null, '(Contact 2.2 Ltd,41414141L,"Fake St., 123",City 2.2,Province 2.2,17487,ES)', '{}') $$,
|
||||
$$ select add_contact(1, 'Contact 2.2', '', 'd@d', '', '(Contact 2.2 Ltd,41414141L,"Fake St., 123",City 2.2,Province 2.2,17487,ES)', '', 'HSBCSKBA', '{}') $$,
|
||||
'Should be able to insert a second contact for the first company with no tag, no phone, and not website'
|
||||
);
|
||||
|
||||
select lives_ok(
|
||||
$$ select add_contact(2, 'Contact 4.1', '999-999-999', 'e@e', 'http://e', '(Contact 4.1 Ltd,42424242Y,"Another Fake St., 123",City 4.1,Province 4.1,17488,ES)', '{tag2}') $$,
|
||||
$$ select add_contact(2, 'Contact 4.1', '999-999-999', 'e@e', 'http://e', '(Contact 4.1 Ltd,42424242Y,"Another Fake St., 123",City 4.1,Province 4.1,17488,ES)', 'MT47JQRS54557143744629565915326', 'ARBNNL22', '{tag2}') $$,
|
||||
'Should be able to insert a contact for the second company with a tag and everything else'
|
||||
);
|
||||
|
||||
select lives_ok(
|
||||
$$ select add_contact(1, 'Contact 2.3', null, null, null, null, '{tag2}') $$,
|
||||
$$ select add_contact(1, 'Contact 2.3', '', '', '', null, '', '', '{tag2}') $$,
|
||||
'Should be able to insert another contact with a repeated tag'
|
||||
);
|
||||
|
||||
|
@ -102,6 +108,22 @@ select bag_eq(
|
|||
'Should have created all contacts’ web'
|
||||
);
|
||||
|
||||
select bag_eq(
|
||||
$$ select name, iban::text from contact join contact_iban using (contact_id) $$,
|
||||
$$ values ('Contact 2.1', 'NL35INGB5262865534')
|
||||
, ('Contact 4.1', 'MT47JQRS54557143744629565915326')
|
||||
$$,
|
||||
'Should have created all contacts’ IBAN'
|
||||
);
|
||||
|
||||
select bag_eq(
|
||||
$$ select name, bic::text from contact join contact_swift using (contact_id) $$,
|
||||
$$ values ('Contact 2.2', 'HSBCSKBA')
|
||||
, ('Contact 4.1', 'ARBNNL22')
|
||||
$$,
|
||||
'Should have created all contacts’ BIC'
|
||||
);
|
||||
|
||||
|
||||
select *
|
||||
from finish();
|
||||
|
|
|
@ -0,0 +1,106 @@
|
|||
-- Test bic
|
||||
set client_min_messages to warning;
|
||||
create extension if not exists pgtap;
|
||||
reset client_min_messages;
|
||||
|
||||
begin;
|
||||
|
||||
select plan(18);
|
||||
|
||||
set search_path to numerus, public;
|
||||
|
||||
select has_domain('bic');
|
||||
select domain_type_is('bic', 'text');
|
||||
|
||||
select lives_ok($$ select 'BBVAESMM'::bic $$, 'Should be able to cast strings without department to bic');
|
||||
select lives_ok($$ select 'LOYDCHGGZCH'::bic $$, 'Should be able to cast strings with department to bic');
|
||||
|
||||
select throws_ok(
|
||||
$$ SELECT 'loydchggzch'::bic $$,
|
||||
23514, null,
|
||||
'Should reject BIC with lowercase'
|
||||
);
|
||||
|
||||
select throws_ok(
|
||||
$$ SELECT ' LOYDCHGGZCH'::bic $$,
|
||||
23514, null,
|
||||
'Should reject BIC with heading spaces'
|
||||
);
|
||||
|
||||
select throws_ok(
|
||||
$$ SELECT 'LOYDCHGGZCH '::bic $$,
|
||||
23514, null,
|
||||
'Should reject BIC with trailing spaces'
|
||||
);
|
||||
|
||||
select throws_ok(
|
||||
$$ SELECT 'LOYD CH GG ZCH'::bic $$,
|
||||
23514, null,
|
||||
'Should reject BIC with middle spaces'
|
||||
);
|
||||
|
||||
select throws_ok(
|
||||
$$ SELECT '1OYDCHGGZCH'::bic $$,
|
||||
23514, null,
|
||||
'Should reject BIC with numbers at first position'
|
||||
);
|
||||
|
||||
select throws_ok(
|
||||
$$ SELECT 'L2YDCHGGZCH'::bic $$,
|
||||
23514, null,
|
||||
'Should reject BIC with numbers at second position'
|
||||
);
|
||||
|
||||
select throws_ok(
|
||||
$$ SELECT 'LO3DCHGGZCH'::bic $$,
|
||||
23514, null,
|
||||
'Should reject BIC with numbers at third position'
|
||||
);
|
||||
|
||||
select throws_ok(
|
||||
$$ SELECT 'LOY4CHGGZCH'::bic $$,
|
||||
23514, null,
|
||||
'Should reject BIC with numbers at fourth position'
|
||||
);
|
||||
|
||||
select throws_ok(
|
||||
$$ SELECT 'LOYD5HGGZCH'::bic $$,
|
||||
23514, null,
|
||||
'Should reject BIC with numbers at fifth position'
|
||||
);
|
||||
|
||||
select throws_ok(
|
||||
$$ SELECT 'LOYDC6GGZCH'::bic $$,
|
||||
23514, null,
|
||||
'Should reject BIC with numbers at sixth position'
|
||||
);
|
||||
|
||||
select throws_ok(
|
||||
$$ SELECT 'LOYDCHG'::bic $$,
|
||||
23514, null,
|
||||
'Should reject BIC with 7 characters'
|
||||
);
|
||||
|
||||
select throws_ok(
|
||||
$$ SELECT 'LOYDCHGGZ'::bic $$,
|
||||
23514, null,
|
||||
'Should reject BIC with 9 characters'
|
||||
);
|
||||
|
||||
select throws_ok(
|
||||
$$ SELECT 'LOYDCHGGZC'::bic $$,
|
||||
23514, null,
|
||||
'Should reject BIC with 10 characters'
|
||||
);
|
||||
|
||||
select throws_ok(
|
||||
$$ SELECT 'LOYDCHGGZCHH'::bic $$,
|
||||
23514, null,
|
||||
'Should reject BIC with 12 characters'
|
||||
);
|
||||
|
||||
|
||||
select *
|
||||
from finish();
|
||||
|
||||
rollback;
|
|
@ -0,0 +1,117 @@
|
|||
-- Test contact_iban
|
||||
set client_min_messages to warning;
|
||||
create extension if not exists pgtap;
|
||||
reset client_min_messages;
|
||||
|
||||
begin;
|
||||
|
||||
select plan(21);
|
||||
|
||||
set search_path to numerus, auth, public;
|
||||
|
||||
select has_table('contact_iban');
|
||||
select has_pk('contact_iban' );
|
||||
select table_privs_are('contact_iban', 'guest', array []::text[]);
|
||||
select table_privs_are('contact_iban', 'invoicer', array ['SELECT', 'INSERT', 'UPDATE', 'DELETE']);
|
||||
select table_privs_are('contact_iban', 'admin', array ['SELECT', 'INSERT', 'UPDATE', 'DELETE']);
|
||||
select table_privs_are('contact_iban', 'authenticator', array []::text[]);
|
||||
|
||||
select has_column('contact_iban', 'contact_id');
|
||||
select col_is_pk('contact_iban', 'contact_id');
|
||||
select col_is_fk('contact_iban', 'contact_id');
|
||||
select fk_ok('contact_iban', 'contact_id', 'contact', 'contact_id');
|
||||
select col_type_is('contact_iban', 'contact_id', 'integer');
|
||||
select col_not_null('contact_iban', 'contact_id');
|
||||
select col_hasnt_default('contact_iban', 'contact_id');
|
||||
|
||||
select has_column('contact_iban', 'iban');
|
||||
select col_type_is('contact_iban', 'iban', 'iban');
|
||||
select col_not_null('contact_iban', 'iban');
|
||||
select col_hasnt_default('contact_iban', 'iban');
|
||||
|
||||
|
||||
set client_min_messages to warning;
|
||||
truncate contact_iban cascade;
|
||||
truncate contact cascade;
|
||||
truncate company_user cascade;
|
||||
truncate payment_method cascade;
|
||||
truncate company cascade;
|
||||
truncate auth."user" cascade;
|
||||
reset client_min_messages;
|
||||
|
||||
set constraints "company_default_payment_method_id_fkey" deferred;
|
||||
|
||||
insert into auth."user" (user_id, email, name, password, role, cookie, cookie_expires_at)
|
||||
values (1, 'demo@tandem.blog', 'Demo', 'test', 'invoicer', '44facbb30d8a419dfd4bfbc44a4b5539d4970148dfc84bed0e', current_timestamp + interval '1 month')
|
||||
, (5, 'admin@tandem.blog', 'Demo', 'test', 'admin', '12af4c88b528c2ad4222e3740496ecbc58e76e26f087657524', current_timestamp + interval '1 month')
|
||||
;
|
||||
|
||||
insert into company (company_id, business_name, vatin, trade_name, phone, email, web, address, city, province, postal_code, country_code, currency_code, default_payment_method_id)
|
||||
values (2, 'Company 2', 'XX123', '', '555-555-555', 'a@a', '', '', '', '', '', 'ES', 'EUR', 222)
|
||||
, (4, 'Company 4', 'XX234', '', '666-666-666', 'b@b', '', '', '', '', '', 'FR', 'USD', 444)
|
||||
;
|
||||
|
||||
insert into payment_method (payment_method_id, company_id, name, instructions)
|
||||
values (444, 4, 'cash', 'cash')
|
||||
, (222, 2, 'cash', 'cash')
|
||||
;
|
||||
|
||||
set constraints "company_default_payment_method_id_fkey" immediate;
|
||||
|
||||
insert into company_user (company_id, user_id)
|
||||
values (2, 1)
|
||||
, (4, 5)
|
||||
;
|
||||
|
||||
insert into contact (contact_id, company_id, name)
|
||||
values (6, 2, 'C1')
|
||||
, (8, 4, 'C2')
|
||||
, (9, 4, 'C3')
|
||||
;
|
||||
|
||||
insert into contact_iban (contact_id, iban)
|
||||
values (6, 'NL35INGB5262865534')
|
||||
, (8, 'MT47JQRS54557143744629565915326')
|
||||
;
|
||||
|
||||
prepare contact_data as
|
||||
select company_id, iban::text
|
||||
from contact
|
||||
join contact_iban using (contact_id)
|
||||
order by company_id, iban;
|
||||
|
||||
set role invoicer;
|
||||
select is_empty('contact_data', 'Should show no data when cookie is not set yet');
|
||||
reset role;
|
||||
|
||||
select set_cookie('44facbb30d8a419dfd4bfbc44a4b5539d4970148dfc84bed0e/demo@tandem.blog');
|
||||
select bag_eq(
|
||||
'contact_data',
|
||||
$$ values (2, 'NL35INGB5262865534')
|
||||
$$,
|
||||
'Should only list contacts of the companies where demo@tandem.blog is user of'
|
||||
);
|
||||
reset role;
|
||||
|
||||
select set_cookie('12af4c88b528c2ad4222e3740496ecbc58e76e26f087657524/admin@tandem.blog');
|
||||
select bag_eq(
|
||||
'contact_data',
|
||||
$$ values (4, 'MT47JQRS54557143744629565915326')
|
||||
$$,
|
||||
'Should only list contacts of the companies where admin@tandem.blog is user of'
|
||||
);
|
||||
reset role;
|
||||
|
||||
select set_cookie('not-a-cookie');
|
||||
select throws_ok(
|
||||
'contact_data',
|
||||
'42501', 'permission denied for table contact',
|
||||
'Should not allow select to guest users'
|
||||
);
|
||||
reset role;
|
||||
|
||||
select *
|
||||
from finish();
|
||||
|
||||
rollback;
|
||||
|
|
@ -0,0 +1,118 @@
|
|||
-- Test contact_swift
|
||||
set client_min_messages to warning;
|
||||
create extension if not exists pgtap;
|
||||
reset client_min_messages;
|
||||
|
||||
begin;
|
||||
|
||||
select plan(21);
|
||||
|
||||
set search_path to numerus, auth, public;
|
||||
|
||||
select has_table('contact_swift');
|
||||
select has_pk('contact_swift' );
|
||||
select table_privs_are('contact_swift', 'guest', array []::text[]);
|
||||
select table_privs_are('contact_swift', 'invoicer', array ['SELECT', 'INSERT', 'UPDATE', 'DELETE']);
|
||||
select table_privs_are('contact_swift', 'admin', array ['SELECT', 'INSERT', 'UPDATE', 'DELETE']);
|
||||
select table_privs_are('contact_swift', 'authenticator', array []::text[]);
|
||||
|
||||
select has_column('contact_swift', 'contact_id');
|
||||
select col_is_pk('contact_swift', 'contact_id');
|
||||
select col_is_fk('contact_swift', 'contact_id');
|
||||
select fk_ok('contact_swift', 'contact_id', 'contact', 'contact_id');
|
||||
select col_type_is('contact_swift', 'contact_id', 'integer');
|
||||
select col_not_null('contact_swift', 'contact_id');
|
||||
select col_hasnt_default('contact_swift', 'contact_id');
|
||||
|
||||
select has_column('contact_swift', 'bic');
|
||||
select col_type_is('contact_swift', 'bic', 'bic');
|
||||
select col_not_null('contact_swift', 'bic');
|
||||
select col_hasnt_default('contact_swift', 'bic');
|
||||
|
||||
|
||||
set client_min_messages to warning;
|
||||
truncate contact_swift cascade;
|
||||
truncate contact cascade;
|
||||
truncate company_user cascade;
|
||||
truncate payment_method cascade;
|
||||
truncate company cascade;
|
||||
truncate auth."user" cascade;
|
||||
reset client_min_messages;
|
||||
|
||||
set constraints "company_default_payment_method_id_fkey" deferred;
|
||||
|
||||
insert into auth."user" (user_id, email, name, password, role, cookie, cookie_expires_at)
|
||||
values (1, 'demo@tandem.blog', 'Demo', 'test', 'invoicer', '44facbb30d8a419dfd4bfbc44a4b5539d4970148dfc84bed0e', current_timestamp + interval '1 month')
|
||||
, (5, 'admin@tandem.blog', 'Demo', 'test', 'admin', '12af4c88b528c2ad4222e3740496ecbc58e76e26f087657524', current_timestamp + interval '1 month')
|
||||
;
|
||||
|
||||
insert into company (company_id, business_name, vatin, trade_name, phone, email, web, address, city, province, postal_code, country_code, currency_code, default_payment_method_id)
|
||||
values (2, 'Company 2', 'XX123', '', '555-555-555', 'a@a', '', '', '', '', '', 'ES', 'EUR', 222)
|
||||
, (4, 'Company 4', 'XX234', '', '666-666-666', 'b@b', '', '', '', '', '', 'FR', 'USD', 444)
|
||||
;
|
||||
|
||||
insert into payment_method (payment_method_id, company_id, name, instructions)
|
||||
values (444, 4, 'cash', 'cash')
|
||||
, (222, 2, 'cash', 'cash')
|
||||
;
|
||||
|
||||
set constraints "company_default_payment_method_id_fkey" immediate;
|
||||
|
||||
insert into company_user (company_id, user_id)
|
||||
values (2, 1)
|
||||
, (4, 5)
|
||||
;
|
||||
|
||||
insert into contact (contact_id, company_id, name)
|
||||
values (6, 2, 'C1')
|
||||
, (8, 4, 'C2')
|
||||
, (9, 4, 'C3')
|
||||
;
|
||||
|
||||
insert into contact_swift (contact_id, bic)
|
||||
values (6, 'HSBCSKBA')
|
||||
, (8, 'ARBNNL22')
|
||||
;
|
||||
|
||||
prepare contact_data as
|
||||
select company_id, bic::text
|
||||
from contact
|
||||
join contact_swift using (contact_id)
|
||||
order by company_id, bic;
|
||||
|
||||
set role invoicer;
|
||||
select is_empty('contact_data', 'Should show no data when cookie is not set yet');
|
||||
reset role;
|
||||
|
||||
select set_cookie('44facbb30d8a419dfd4bfbc44a4b5539d4970148dfc84bed0e/demo@tandem.blog');
|
||||
select bag_eq(
|
||||
'contact_data',
|
||||
$$ values (2, 'HSBCSKBA')
|
||||
$$,
|
||||
'Should only list contacts of the companies where demo@tandem.blog is user of'
|
||||
);
|
||||
reset role;
|
||||
|
||||
select set_cookie('12af4c88b528c2ad4222e3740496ecbc58e76e26f087657524/admin@tandem.blog');
|
||||
select bag_eq(
|
||||
'contact_data',
|
||||
$$ values (4, 'ARBNNL22')
|
||||
$$,
|
||||
'Should only list contacts of the companies where admin@tandem.blog is user of'
|
||||
);
|
||||
reset role;
|
||||
|
||||
select set_cookie('not-a-cookie');
|
||||
select throws_ok(
|
||||
'contact_data',
|
||||
'42501', 'permission denied for table contact',
|
||||
'Should not allow select to guest users'
|
||||
);
|
||||
reset role;
|
||||
|
||||
|
||||
select *
|
||||
from finish();
|
||||
|
||||
rollback;
|
||||
|
|
@ -5,22 +5,28 @@ reset client_min_messages;
|
|||
|
||||
begin;
|
||||
|
||||
select plan(17);
|
||||
select plan(19);
|
||||
|
||||
set search_path to auth, numerus, public;
|
||||
|
||||
select has_function('numerus', 'edit_contact', array ['uuid', 'text', 'text', 'email', 'uri', 'tax_details', 'tag_name[]']);
|
||||
select function_lang_is('numerus', 'edit_contact', array ['uuid', 'text', 'text', 'email', 'uri', 'tax_details', 'tag_name[]'], 'plpgsql');
|
||||
select function_returns('numerus', 'edit_contact', array ['uuid', 'text', 'text', 'email', 'uri', 'tax_details', 'tag_name[]'], 'uuid');
|
||||
select isnt_definer('numerus', 'edit_contact', array ['uuid', 'text', 'text', 'email', 'uri', 'tax_details', 'tag_name[]']);
|
||||
select volatility_is('numerus', 'edit_contact', array ['uuid', 'text', 'text', 'email', 'uri', 'tax_details', 'tag_name[]'], 'volatile');
|
||||
select function_privs_are('numerus', 'edit_contact', array ['uuid', 'text', 'text', 'email', 'uri', 'tax_details', 'tag_name[]'], 'guest', array []::text[]);
|
||||
select function_privs_are('numerus', 'edit_contact', array ['uuid', 'text', 'text', 'email', 'uri', 'tax_details', 'tag_name[]'], 'invoicer', array ['EXECUTE']);
|
||||
select function_privs_are('numerus', 'edit_contact', array ['uuid', 'text', 'text', 'email', 'uri', 'tax_details', 'tag_name[]'], 'admin', array ['EXECUTE']);
|
||||
select function_privs_are('numerus', 'edit_contact', array ['uuid', 'text', 'text', 'email', 'uri', 'tax_details', 'tag_name[]'], 'authenticator', array []::text[]);
|
||||
select has_function('numerus', 'edit_contact', array ['uuid', 'text', 'text', 'text', 'text', 'tax_details', 'text', 'text', 'tag_name[]']);
|
||||
select function_lang_is('numerus', 'edit_contact', array ['uuid', 'text', 'text', 'text', 'text', 'tax_details', 'text', 'text', 'tag_name[]'], 'plpgsql');
|
||||
select function_returns('numerus', 'edit_contact', array ['uuid', 'text', 'text', 'text', 'text', 'tax_details', 'text', 'text', 'tag_name[]'], 'uuid');
|
||||
select isnt_definer('numerus', 'edit_contact', array ['uuid', 'text', 'text', 'text', 'text', 'tax_details', 'text', 'text', 'tag_name[]']);
|
||||
select volatility_is('numerus', 'edit_contact', array ['uuid', 'text', 'text', 'text', 'text', 'tax_details', 'text', 'text', 'tag_name[]'], 'volatile');
|
||||
select function_privs_are('numerus', 'edit_contact', array ['uuid', 'text', 'text', 'text', 'text', 'tax_details', 'text', 'text', 'tag_name[]'], 'guest', array []::text[]);
|
||||
select function_privs_are('numerus', 'edit_contact', array ['uuid', 'text', 'text', 'text', 'text', 'tax_details', 'text', 'text', 'tag_name[]'], 'invoicer', array ['EXECUTE']);
|
||||
select function_privs_are('numerus', 'edit_contact', array ['uuid', 'text', 'text', 'text', 'text', 'tax_details', 'text', 'text', 'tag_name[]'], 'admin', array ['EXECUTE']);
|
||||
select function_privs_are('numerus', 'edit_contact', array ['uuid', 'text', 'text', 'text', 'text', 'tax_details', 'text', 'text', 'tag_name[]'], 'authenticator', array []::text[]);
|
||||
|
||||
|
||||
set client_min_messages to warning;
|
||||
truncate contact_swift cascade;
|
||||
truncate contact_iban cascade;
|
||||
truncate contact_web cascade;
|
||||
truncate contact_email cascade;
|
||||
truncate contact_phone cascade;
|
||||
truncate contact_tax_details cascade;
|
||||
truncate contact cascade;
|
||||
truncate payment_method cascade;
|
||||
truncate company cascade;
|
||||
|
@ -66,19 +72,29 @@ values (12, 'https://1/')
|
|||
, (13, 'https://2/')
|
||||
;
|
||||
|
||||
insert into contact_iban (contact_id, iban)
|
||||
values (12, 'NL04RABO9373475770')
|
||||
, (13, 'NL17RABO4416709382')
|
||||
;
|
||||
|
||||
insert into contact_swift (contact_id, bic)
|
||||
values (12, 'ABNANL2A')
|
||||
, (13, 'ARBNNL22')
|
||||
;
|
||||
|
||||
|
||||
select lives_ok(
|
||||
$$ select edit_contact('7ac3ae0e-b0c1-4206-a19b-0be20835edd4', 'Contact 2.1', '999-999-999', 'c1@c1', 'https://c', '(Contact 2.1 Ltd,40404040D,"Fake St., 123",City 2.1,Province 2.1,19486,ES)', array['tag1']) $$,
|
||||
$$ select edit_contact('7ac3ae0e-b0c1-4206-a19b-0be20835edd4', 'Contact 2.1', '999-999-999', 'c1@c1', 'https://c', '(Contact 2.1 Ltd,40404040D,"Fake St., 123",City 2.1,Province 2.1,19486,ES)', 'NL68RABO7792285766', '', array['tag1']) $$,
|
||||
'Should be able to edit the first contact'
|
||||
);
|
||||
|
||||
select lives_ok(
|
||||
$$ select edit_contact('b57b980b-247b-4be4-a0b7-03a7819c53ae', 'Contact 2.2', null, null, null, null, array['tag1', 'tag3']) $$,
|
||||
$$ select edit_contact('b57b980b-247b-4be4-a0b7-03a7819c53ae', 'Contact 2.2', '', '', '', null, '', 'ASNBNL21', array['tag1', 'tag3']) $$,
|
||||
'Should be able to edit the second contact'
|
||||
);
|
||||
|
||||
select lives_ok(
|
||||
$$ select edit_contact('12fd031b-8f4d-4ac1-9dde-7df336dc6d52', 'Contact 2.3', '111-111-111', 'd2@d2', 'https://d', '(Contact 2.3 Ltd,41414141L,"Another Fake St., 123",City 2.2,Province 2.2,17417,ES)', array['tag2']) $$,
|
||||
$$ select edit_contact('12fd031b-8f4d-4ac1-9dde-7df336dc6d52', 'Contact 2.3', '111-111-111', 'd2@d2', 'https://d', '(Contact 2.3 Ltd,41414141L,"Another Fake St., 123",City 2.2,Province 2.2,17417,ES)', 'NL48RABO6482008283', 'BOFSNL21002', array['tag2']) $$,
|
||||
'Should be able to edit the third contact'
|
||||
);
|
||||
|
||||
|
@ -123,6 +139,22 @@ select bag_eq(
|
|||
'Should have updated all contacts’ web'
|
||||
);
|
||||
|
||||
select bag_eq(
|
||||
$$ select name, iban::text from contact join contact_iban using (contact_id) $$,
|
||||
$$ values ('Contact 2.1', 'NL68RABO7792285766')
|
||||
, ('Contact 2.3', 'NL48RABO6482008283')
|
||||
$$,
|
||||
'Should have updated all contacts’ IBAN'
|
||||
);
|
||||
|
||||
select bag_eq(
|
||||
$$ select name, bic::text from contact join contact_swift using (contact_id) $$,
|
||||
$$ values ('Contact 2.2', 'ASNBNL21')
|
||||
, ('Contact 2.3', 'BOFSNL21002')
|
||||
$$,
|
||||
'Should have updated all contacts’ BIC'
|
||||
);
|
||||
|
||||
|
||||
select *
|
||||
from finish();
|
||||
|
|
|
@ -9,9 +9,10 @@ select plan(1);
|
|||
|
||||
select extensions_are(array[
|
||||
'citext'
|
||||
, 'iban'
|
||||
, 'pgcrypto'
|
||||
, 'pg_libphonenumber'
|
||||
, 'pgtap'
|
||||
, 'pgcrypto'
|
||||
, 'plpgsql'
|
||||
, 'uri'
|
||||
, 'vat'
|
||||
|
|
|
@ -2,6 +2,6 @@
|
|||
|
||||
begin;
|
||||
|
||||
select has_function_privilege('numerus.add_contact(integer, text, text, numerus.email, uri, numerus.tax_details, numerus.tag_name[])', 'execute');
|
||||
select has_function_privilege('numerus.add_contact(integer, text, text, text, text, numerus.tax_details, text, text, numerus.tag_name[])', 'execute');
|
||||
|
||||
rollback;
|
||||
|
|
|
@ -0,0 +1,7 @@
|
|||
-- Verify numerus:bic on pg
|
||||
|
||||
begin;
|
||||
|
||||
select pg_catalog.has_type_privilege('numerus.bic', 'usage');
|
||||
|
||||
rollback;
|
|
@ -0,0 +1,13 @@
|
|||
-- Verify numerus:contact_iban on pg
|
||||
|
||||
begin;
|
||||
|
||||
select contact_id
|
||||
, iban
|
||||
from numerus.contact_iban
|
||||
where false;
|
||||
|
||||
select 1 / count(*) from pg_class where oid = 'numerus.contact_iban'::regclass and relrowsecurity;
|
||||
select 1 / count(*) from pg_policy where polname = 'company_policy' and polrelid = 'numerus.contact_iban'::regclass;
|
||||
|
||||
rollback;
|
|
@ -0,0 +1,13 @@
|
|||
-- Verify numerus:contact_swift on pg
|
||||
|
||||
begin;
|
||||
|
||||
select contact_id
|
||||
, bic
|
||||
from numerus.contact_swift
|
||||
where false;
|
||||
|
||||
select 1 / count(*) from pg_class where oid = 'numerus.contact_swift'::regclass and relrowsecurity;
|
||||
select 1 / count(*) from pg_policy where polname = 'company_policy' and polrelid = 'numerus.contact_swift'::regclass;
|
||||
|
||||
rollback;
|
|
@ -2,6 +2,6 @@
|
|||
|
||||
begin;
|
||||
|
||||
select has_function_privilege('numerus.edit_contact(uuid, text, text, numerus.email, uri, numerus.tax_details, numerus.tag_name[])', 'execute');
|
||||
select has_function_privilege('numerus.edit_contact(uuid, text, text, text, text, numerus.tax_details, text, text, numerus.tag_name[])', 'execute');
|
||||
|
||||
rollback;
|
||||
|
|
|
@ -0,0 +1,7 @@
|
|||
-- Verify numerus:extension_iban on pg
|
||||
|
||||
begin;
|
||||
|
||||
select 1/count(*) from pg_extension where extname = 'iban';
|
||||
|
||||
rollback;
|
|
@ -23,25 +23,30 @@
|
|||
{{ putMethod }}
|
||||
|
||||
{{ with .Form }}
|
||||
<div class="contact-data">
|
||||
{{ template "input-field" .Name }}
|
||||
{{ template "input-field" .Phone }}
|
||||
{{ template "input-field" .Email }}
|
||||
{{ template "input-field" .Web }}
|
||||
{{ template "tags-field" .Tags }}
|
||||
</div>
|
||||
<fieldset class="contact-data">
|
||||
{{ template "input-field" .Name }}
|
||||
{{ template "input-field" .Phone }}
|
||||
{{ template "input-field" .Email }}
|
||||
{{ template "input-field" .Web }}
|
||||
{{ template "tags-field" .Tags }}
|
||||
</fieldset>
|
||||
|
||||
{{ template "check-field" .HasTaxDetails }}
|
||||
<fieldset class="contact-data">
|
||||
{{ template "input-field" .IBAN }}
|
||||
{{ template "input-field" .BIC }}
|
||||
</fieldset>
|
||||
|
||||
<div class="contact-data contact-tax-details">
|
||||
{{ template "input-field" .BusinessName }}
|
||||
{{ template "input-field" .VATIN }}
|
||||
{{ template "input-field" .Address }}
|
||||
{{ template "input-field" .City }}
|
||||
{{ template "input-field" .Province }}
|
||||
{{ template "input-field" .PostalCode }}
|
||||
{{ template "select-field" .Country }}
|
||||
</div>
|
||||
{{ template "check-field" .HasTaxDetails }}
|
||||
|
||||
<fieldset class="contact-data contact-tax-details">
|
||||
{{ template "input-field" .BusinessName }}
|
||||
{{ template "input-field" .VATIN }}
|
||||
{{ template "input-field" .Address }}
|
||||
{{ template "input-field" .City }}
|
||||
{{ template "input-field" .Province }}
|
||||
{{ template "input-field" .PostalCode }}
|
||||
{{ template "select-field" .Country }}
|
||||
</fieldset>
|
||||
{{ end }}
|
||||
|
||||
<fieldset>
|
||||
|
|
|
@ -20,17 +20,22 @@
|
|||
<form method="POST" action="{{ companyURI "/contacts" }}" data-hx-boost="true">
|
||||
{{ csrfToken }}
|
||||
|
||||
<div class="contact-data">
|
||||
<fieldset class="contact-data">
|
||||
{{ template "input-field" .Name | addInputAttr "autofocus" }}
|
||||
{{ template "input-field" .Phone }}
|
||||
{{ template "input-field" .Email }}
|
||||
{{ template "input-field" .Web }}
|
||||
{{ template "tags-field" .Tags }}
|
||||
</div>
|
||||
</fieldset>
|
||||
|
||||
<fieldset class="contact-data">
|
||||
{{ template "input-field" .IBAN }}
|
||||
{{ template "input-field" .BIC }}
|
||||
</fieldset>
|
||||
|
||||
{{ template "check-field" .HasTaxDetails }}
|
||||
|
||||
<div class="contact-data contact-tax-details">
|
||||
<fieldset class="contact-data contact-tax-details">
|
||||
{{ template "input-field" .BusinessName }}
|
||||
{{ template "input-field" .VATIN }}
|
||||
{{ template "input-field" .Address }}
|
||||
|
@ -38,7 +43,7 @@
|
|||
{{ template "input-field" .Province }}
|
||||
{{ template "input-field" .PostalCode }}
|
||||
{{ template "select-field" .Country }}
|
||||
</div>
|
||||
</fieldset>
|
||||
|
||||
<fieldset>
|
||||
<button formnovalidate class="primary" type="submit">{{( pgettext "Save" "action" )}}</button>
|
||||
|
|
Loading…
Reference in New Issue