Re-implemented guessing of next document id.
Signed-off-by: Stephan Richter <s.richter@srsoftware.de>
This commit is contained in:
@@ -9,7 +9,6 @@ import java.util.regex.Pattern;
|
|||||||
public class Constants {
|
public class Constants {
|
||||||
private Constants(){}
|
private Constants(){}
|
||||||
|
|
||||||
|
|
||||||
public static final Pattern POST_CODE = compile("(.*\\w+.*)\n(.*\\d+.*)\n(\\d{5}) (\\w+)",DOTALL);
|
public static final Pattern POST_CODE = compile("(.*\\w+.*)\n(.*\\d+.*)\n(\\d{5}) (\\w+)",DOTALL);
|
||||||
|
|
||||||
public static final String CLONE = "clone";
|
public static final String CLONE = "clone";
|
||||||
@@ -21,8 +20,6 @@ public class Constants {
|
|||||||
|
|
||||||
public static final String ERROR_ADDRESS_MISSING = "{0} address does not contain street address / post code / city";
|
public static final String ERROR_ADDRESS_MISSING = "{0} address does not contain street address / post code / city";
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
public static final String MOVE = "move";
|
public static final String MOVE = "move";
|
||||||
|
|
||||||
public static final String PATH_ADD_ITEM = "add_item";
|
public static final String PATH_ADD_ITEM = "add_item";
|
||||||
@@ -38,8 +35,6 @@ public class Constants {
|
|||||||
public static final String POSITION = "position";
|
public static final String POSITION = "position";
|
||||||
public static final String PROJECT_ID = "project_id";
|
public static final String PROJECT_ID = "project_id";
|
||||||
|
|
||||||
|
|
||||||
public static final String TABLE_COMPANY_SETTINGS = "company_settings";
|
|
||||||
public static final String TABLE_CUSTOMER_SETTINGS = "company_customer_settings";
|
public static final String TABLE_CUSTOMER_SETTINGS = "company_customer_settings";
|
||||||
public static final String TABLE_DOCUMENTS = "documents";
|
public static final String TABLE_DOCUMENTS = "documents";
|
||||||
public static final String TABLE_DOCUMENT_TYPES = "document_types";
|
public static final String TABLE_DOCUMENT_TYPES = "document_types";
|
||||||
@@ -47,4 +42,9 @@ public class Constants {
|
|||||||
public static final String TABLE_PRICES = "customer_prices";
|
public static final String TABLE_PRICES = "customer_prices";
|
||||||
public static final String TABLE_TEMPLATES = "templates";
|
public static final String TABLE_TEMPLATES = "templates";
|
||||||
public static final String TEMPLATES = "templates";
|
public static final String TEMPLATES = "templates";
|
||||||
|
|
||||||
|
public static final String TYPE_CONFIRMATION = "confirmation";
|
||||||
|
public static final String TYPE_INVOICE = "invoice";
|
||||||
|
public static final String TYPE_OFFER = "offer";
|
||||||
|
public static final String TYPE_REMINDER = "reminder";
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -432,8 +432,7 @@ public class DocumentApi extends BaseHandler implements DocumentService {
|
|||||||
|
|
||||||
Document doc = getDocument(docId, user).a;
|
Document doc = getDocument(docId, user).a;
|
||||||
|
|
||||||
var companySettings = db.getCompanySettings(doc.companyId(),docType);
|
var nextNumber = db.nextDocId(user.language(),doc.companyId(),docType);
|
||||||
var nextNumber = companySettings.nextDocId();
|
|
||||||
|
|
||||||
Document clone = new Document(
|
Document clone = new Document(
|
||||||
0,
|
0,
|
||||||
@@ -469,19 +468,17 @@ public class DocumentApi extends BaseHandler implements DocumentService {
|
|||||||
if (!json.has(TYPE) || !(json.get(TYPE) instanceof Number docTypeId)) throw missingFieldException(TYPE);
|
if (!json.has(TYPE) || !(json.get(TYPE) instanceof Number docTypeId)) throw missingFieldException(TYPE);
|
||||||
var type = db.getType(docTypeId.intValue());
|
var type = db.getType(docTypeId.intValue());
|
||||||
var customer = Customer.of(customerData);
|
var customer = Customer.of(customerData);
|
||||||
Template template = new Template(6,companyId,"unknwon",null);
|
|
||||||
String currency = company.currency();
|
String currency = company.currency();
|
||||||
String sep = company.decimalSeparator();
|
String sep = company.decimalSeparator();
|
||||||
var settings = db.getCustomerSettings(companyId,type,customer.id());
|
var settings = db.getCustomerSettings(companyId,type,customer.id());
|
||||||
var newCustomer = settings == null;
|
var newCustomer = settings == null;
|
||||||
if (newCustomer) settings = CustomerSettings.empty();
|
if (newCustomer) settings = CustomerSettings.empty();
|
||||||
var companySettings = db.getCompanySettings(companyId,type);
|
var nextNumber = db.nextDocId(user.language(), companyId,type);
|
||||||
var nextNumber = companySettings.nextDocId();
|
|
||||||
String lastHead = settings.header();
|
String lastHead = settings.header();
|
||||||
String lastFooter = settings.footer();
|
String lastFooter = settings.footer();
|
||||||
var sender = Sender.of(senderData);
|
var sender = Sender.of(senderData);
|
||||||
LOG.log(DEBUG,json.toString(2));
|
LOG.log(DEBUG,json.toString(2));
|
||||||
var doc = new Document(0,companyId,nextNumber,type, LocalDate.now(), NEW,template,null,lastHead,lastFooter,currency,sep,sender,customer,new PositionList());
|
var doc = new Document(0,companyId,nextNumber,type, LocalDate.now(), NEW,null,null,lastHead,lastFooter,currency,sep,sender,customer,new PositionList());
|
||||||
var saved = db.save(doc);
|
var saved = db.save(doc);
|
||||||
if (newCustomer) {
|
if (newCustomer) {
|
||||||
if (customerData.get(CONTACT_ID) instanceof Number contactId) {
|
if (customerData.get(CONTACT_ID) instanceof Number contactId) {
|
||||||
@@ -491,7 +488,6 @@ public class DocumentApi extends BaseHandler implements DocumentService {
|
|||||||
}
|
}
|
||||||
companyService().saveNewCustomer(companyId,customer.id());
|
companyService().saveNewCustomer(companyId,customer.id());
|
||||||
}
|
}
|
||||||
db.step(companySettings);
|
|
||||||
return sendContent(ex,saved);
|
return sendContent(ex,saved);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -27,8 +27,6 @@ public interface DocumentDb {
|
|||||||
|
|
||||||
CustomerSettings getCustomerSettings(long companyId, Type docType, String customerId) throws UmbrellaException;
|
CustomerSettings getCustomerSettings(long companyId, Type docType, String customerId) throws UmbrellaException;
|
||||||
|
|
||||||
CompanySettings getCompanySettings(long companyId, Type docType) throws UmbrellaException;
|
|
||||||
|
|
||||||
Collection<Template> getCompanyTemplates(long l) throws UmbrellaException;
|
Collection<Template> getCompanyTemplates(long l) throws UmbrellaException;
|
||||||
|
|
||||||
Type getType(int typeId) throws UmbrellaException;
|
Type getType(int typeId) throws UmbrellaException;
|
||||||
@@ -39,12 +37,7 @@ public interface DocumentDb {
|
|||||||
|
|
||||||
Document loadDoc(long docId) throws UmbrellaException;
|
Document loadDoc(long docId) throws UmbrellaException;
|
||||||
|
|
||||||
/**
|
String nextDocId(String language, long companyId, Type type);
|
||||||
* decrement the document number
|
|
||||||
* @param companyId
|
|
||||||
* @param type
|
|
||||||
*/
|
|
||||||
void rollback(long companyId, Type type) throws UmbrellaException;
|
|
||||||
|
|
||||||
Document save(Document document) throws UmbrellaException;
|
Document save(Document document) throws UmbrellaException;
|
||||||
|
|
||||||
@@ -52,11 +45,5 @@ public interface DocumentDb {
|
|||||||
|
|
||||||
CustomerSettings save(long companyId, Type docType, String customerId, CustomerSettings settings) throws UmbrellaException;
|
CustomerSettings save(long companyId, Type docType, String customerId, CustomerSettings settings) throws UmbrellaException;
|
||||||
|
|
||||||
/**
|
|
||||||
* increment the document number
|
|
||||||
* @param settings containing company id and document type
|
|
||||||
*/
|
|
||||||
void step(CompanySettings settings);
|
|
||||||
|
|
||||||
Pair<Integer> switchPositions(long docId, Pair<Integer> longPair) throws UmbrellaException;
|
Pair<Integer> switchPositions(long docId, Pair<Integer> longPair) throws UmbrellaException;
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -10,6 +10,7 @@ import static de.srsoftware.umbrella.core.Field.*;
|
|||||||
import static de.srsoftware.umbrella.core.Field.COMPANY_ID;
|
import static de.srsoftware.umbrella.core.Field.COMPANY_ID;
|
||||||
import static de.srsoftware.umbrella.core.Field.TAX;
|
import static de.srsoftware.umbrella.core.Field.TAX;
|
||||||
import static de.srsoftware.umbrella.core.Field.UNIT;
|
import static de.srsoftware.umbrella.core.Field.UNIT;
|
||||||
|
import static de.srsoftware.umbrella.core.ModuleRegistry.translator;
|
||||||
import static de.srsoftware.umbrella.core.exceptions.UmbrellaException.databaseException;
|
import static de.srsoftware.umbrella.core.exceptions.UmbrellaException.databaseException;
|
||||||
import static de.srsoftware.umbrella.core.model.Document.DEFAULT_THOUSANDS_SEPARATOR;
|
import static de.srsoftware.umbrella.core.model.Document.DEFAULT_THOUSANDS_SEPARATOR;
|
||||||
import static de.srsoftware.umbrella.core.model.Document.State;
|
import static de.srsoftware.umbrella.core.model.Document.State;
|
||||||
@@ -20,6 +21,7 @@ import static java.time.ZoneOffset.UTC;
|
|||||||
|
|
||||||
import de.srsoftware.tools.Pair;
|
import de.srsoftware.tools.Pair;
|
||||||
import de.srsoftware.tools.jdbc.Query;
|
import de.srsoftware.tools.jdbc.Query;
|
||||||
|
import de.srsoftware.umbrella.core.BaseDb;
|
||||||
import de.srsoftware.umbrella.core.exceptions.UmbrellaException;
|
import de.srsoftware.umbrella.core.exceptions.UmbrellaException;
|
||||||
import de.srsoftware.umbrella.core.model.*;
|
import de.srsoftware.umbrella.core.model.*;
|
||||||
import de.srsoftware.umbrella.documents.model.*;
|
import de.srsoftware.umbrella.documents.model.*;
|
||||||
@@ -28,30 +30,33 @@ import java.sql.ResultSet;
|
|||||||
import java.sql.SQLException;
|
import java.sql.SQLException;
|
||||||
import java.time.Instant;
|
import java.time.Instant;
|
||||||
import java.util.*;
|
import java.util.*;
|
||||||
|
import java.util.regex.Pattern;
|
||||||
|
|
||||||
public class SqliteDb implements DocumentDb{
|
public class SqliteDb extends BaseDb implements DocumentDb{
|
||||||
private static final System.Logger LOG = System.getLogger(SqliteDb.class.getSimpleName());
|
private static final System.Logger LOG = System.getLogger(SqliteDb.class.getSimpleName());
|
||||||
private final Connection db;
|
|
||||||
private static final String DB_VERSION = "message_db_version";
|
private static final String DB_VERSION = "message_db_version";
|
||||||
private static final int INITIAL_DB_VERSION = 1;
|
private static final int INITIAL_DB_VERSION = 1;
|
||||||
|
private static final Pattern NUMBER_PATTERN = Pattern.compile("(\\D*)(\\d+)(.*)");
|
||||||
|
|
||||||
public SqliteDb(Connection conn){
|
public SqliteDb(Connection connection) {
|
||||||
db = conn;
|
super(connection);
|
||||||
init();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private int createTables() {
|
protected int createTables() {
|
||||||
createTableDocumentTypes();
|
int currentVersion = createSettingsTable();
|
||||||
createTableTemplates();
|
switch (currentVersion) {
|
||||||
createTableDocuments();
|
case 0:
|
||||||
createTablePositions();
|
createTableDocumentTypes();
|
||||||
createTableCustomerPrices();
|
createTableTemplates();
|
||||||
createTableCompanySettings();
|
createTableDocuments();
|
||||||
createTableCustomerSettings();
|
createTablePositions();
|
||||||
return createTableSettings();
|
createTableCustomerPrices();
|
||||||
|
createTableCustomerSettings();
|
||||||
|
}
|
||||||
|
return setCurrentVersion(1);
|
||||||
}
|
}
|
||||||
|
|
||||||
private void createTableCompanySettings() {
|
/*private void createTableCompanySettings() {
|
||||||
var sql = "CREATE TABLE IF NOT EXISTS {0} ({1} INT NOT NULL, {2} INT NOT NULL, {3} TEXT DEFAULT \"A\", {4} TEXT DEFAULT NULL, {5} INT NOT NULL DEFAULT 1, PRIMARY KEY ({1}, {2}))";
|
var sql = "CREATE TABLE IF NOT EXISTS {0} ({1} INT NOT NULL, {2} INT NOT NULL, {3} TEXT DEFAULT \"A\", {4} TEXT DEFAULT NULL, {5} INT NOT NULL DEFAULT 1, PRIMARY KEY ({1}, {2}))";
|
||||||
try {
|
try {
|
||||||
var stmt = db.prepareStatement(format(sql,TABLE_COMPANY_SETTINGS, COMPANY_ID,DOC_TYPE_ID,TYPE_PREFIX,TYPE_SUFFIX,TYPE_NUMBER));
|
var stmt = db.prepareStatement(format(sql,TABLE_COMPANY_SETTINGS, COMPANY_ID,DOC_TYPE_ID,TYPE_PREFIX,TYPE_SUFFIX,TYPE_NUMBER));
|
||||||
@@ -61,7 +66,7 @@ public class SqliteDb implements DocumentDb{
|
|||||||
LOG.log(ERROR,ERROR_FAILED_CREATE_TABLE,TABLE_COMPANY_SETTINGS,e);
|
LOG.log(ERROR,ERROR_FAILED_CREATE_TABLE,TABLE_COMPANY_SETTINGS,e);
|
||||||
throw new RuntimeException(e);
|
throw new RuntimeException(e);
|
||||||
}
|
}
|
||||||
}
|
}*/
|
||||||
|
|
||||||
private void createTableCustomerPrices() {
|
private void createTableCustomerPrices() {
|
||||||
var sql = "CREATE TABLE IF NOT EXISTS {0} ({1} INT NOT NULL, {2} VARCHAR(255), {3} VARCHAR(50), {4} INTEGER)";
|
var sql = "CREATE TABLE IF NOT EXISTS {0} ({1} INT NOT NULL, {2} VARCHAR(255), {3} VARCHAR(50), {4} INTEGER)";
|
||||||
@@ -82,7 +87,7 @@ public class SqliteDb implements DocumentDb{
|
|||||||
stmt.execute();
|
stmt.execute();
|
||||||
stmt.close();
|
stmt.close();
|
||||||
} catch (SQLException e) {
|
} catch (SQLException e) {
|
||||||
LOG.log(ERROR,ERROR_FAILED_CREATE_TABLE,TABLE_COMPANY_SETTINGS,e);
|
LOG.log(ERROR,ERROR_FAILED_CREATE_TABLE,TABLE_CUSTOMER_SETTINGS,e);
|
||||||
throw new RuntimeException(e);
|
throw new RuntimeException(e);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -96,8 +101,8 @@ CREATE TABLE IF NOT EXISTS {0} (
|
|||||||
{3} INT NOT NULL,
|
{3} INT NOT NULL,
|
||||||
{4} TEXT NOT NULL,
|
{4} TEXT NOT NULL,
|
||||||
{5} TIMESTAMP NOT NULL,
|
{5} TIMESTAMP NOT NULL,
|
||||||
{6} INT NOT NULL NULL,
|
{6} INT NOT NULL,
|
||||||
{7} INT NOT NULL,
|
{7} INT,
|
||||||
{8} VARCHAR(100),
|
{8} VARCHAR(100),
|
||||||
{9} TEXT,
|
{9} TEXT,
|
||||||
{10} TEXT,
|
{10} TEXT,
|
||||||
@@ -128,6 +133,12 @@ CREATE TABLE IF NOT EXISTS {0} (
|
|||||||
var stmt = db.prepareStatement(format(createTable,TABLE_DOCUMENT_TYPES, ID,NEXT_TYPE, NAME));
|
var stmt = db.prepareStatement(format(createTable,TABLE_DOCUMENT_TYPES, ID,NEXT_TYPE, NAME));
|
||||||
stmt.execute();
|
stmt.execute();
|
||||||
stmt.close();
|
stmt.close();
|
||||||
|
insertInto(TABLE_DOCUMENT_TYPES,ID,NEXT_TYPE,NAME)
|
||||||
|
.values(1,2,TYPE_OFFER)
|
||||||
|
.values(2,3,TYPE_CONFIRMATION)
|
||||||
|
.values(3,4,TYPE_INVOICE)
|
||||||
|
.values(4,4,TYPE_REMINDER)
|
||||||
|
.execute(db);
|
||||||
} catch (SQLException e) {
|
} catch (SQLException e) {
|
||||||
LOG.log(ERROR,ERROR_FAILED_CREATE_TABLE,TABLE_DOCUMENT_TYPES,e);
|
LOG.log(ERROR,ERROR_FAILED_CREATE_TABLE,TABLE_DOCUMENT_TYPES,e);
|
||||||
throw new RuntimeException(e);
|
throw new RuntimeException(e);
|
||||||
@@ -241,22 +252,10 @@ CREATE TABLE IF NOT EXISTS {0} ( {1} VARCHAR(255) PRIMARY KEY, {2} VARCHAR(255)
|
|||||||
return pos;
|
return pos;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public CompanySettings getCompanySettings(long companyId, Type docType) throws UmbrellaException {
|
|
||||||
try {
|
|
||||||
var rs = select(ALL).from(TABLE_COMPANY_SETTINGS).where(COMPANY_ID,equal(companyId)).where(DOC_TYPE_ID,equal(docType.id())).exec(db);
|
|
||||||
CompanySettings settings = null;
|
|
||||||
if (rs.next()) settings = CompanySettings.of(rs);
|
|
||||||
rs.close();
|
|
||||||
if (settings != null) return settings;
|
|
||||||
} catch (SQLException ignored) {
|
|
||||||
}
|
|
||||||
throw databaseException("Failed to load customer settings (company: {0}, document type: {1})",companyId, docType.name());
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Collection<Template> getCompanyTemplates(long companyId) throws UmbrellaException {
|
public Collection<Template> getCompanyTemplates(long companyId) throws UmbrellaException {
|
||||||
try {
|
try {
|
||||||
|
|
||||||
var rs = select(ALL).from(TABLE_TEMPLATES).where(COMPANY_ID,equal(companyId)).exec(db);
|
var rs = select(ALL).from(TABLE_TEMPLATES).where(COMPANY_ID,equal(companyId)).exec(db);
|
||||||
var templates = new HashSet<Template>();
|
var templates = new HashSet<Template>();
|
||||||
while (rs.next()) templates.add(Template.of(rs));
|
while (rs.next()) templates.add(Template.of(rs));
|
||||||
@@ -454,21 +453,28 @@ CREATE TABLE IF NOT EXISTS {0} ( {1} VARCHAR(255) PRIMARY KEY, {2} VARCHAR(255)
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void rollback(long companyId, Type type) throws UmbrellaException {
|
public String nextDocId(String language, long companyId, Type type) {
|
||||||
try {
|
try {
|
||||||
var settings = getCompanySettings(companyId,type);
|
var rs = select(NUMBER).from(TABLE_DOCUMENTS).where(COMPANY_ID,equal(companyId)).where(TYPE_ID,equal(type.id())).sort(ID+" DESC").limit(1).exec(db);
|
||||||
|
String lastId = null;
|
||||||
var numbers = new HashSet<String>();
|
if (rs.next()) lastId = rs.getString(1);
|
||||||
var rs = select(NUMBER).from(TABLE_DOCUMENTS).where(COMPANY_ID,equal(companyId)).exec(db);
|
|
||||||
while (rs.next()) numbers.add(rs.getString(NUMBER));
|
|
||||||
rs.close();
|
rs.close();
|
||||||
|
if (lastId == null) return translator().translate(language,type.name())+"-0001";
|
||||||
var previous = settings.previous();
|
var numeric = NUMBER_PATTERN.matcher(lastId);
|
||||||
while (previous.isPresent() && !numbers.contains(previous.get().nextDocId())) previous = previous.get().previous();
|
if (numeric.find()){
|
||||||
|
var prefix = numeric.group(1);
|
||||||
previous.ifPresent(this::step);
|
var digits = numeric.group(2);
|
||||||
} catch (SQLException e){
|
var suffix = numeric.group(3);
|
||||||
// TODO
|
var len = digits.length();
|
||||||
|
while (digits.startsWith("0")) digits = digits.substring(1);
|
||||||
|
var lid = Long.parseLong(digits)+1;
|
||||||
|
digits = ""+lid;
|
||||||
|
while (digits.length()<len) digits = "0"+digits;
|
||||||
|
return prefix+digits+suffix;
|
||||||
|
}
|
||||||
|
return lastId;
|
||||||
|
} catch (SQLException e) {
|
||||||
|
throw databaseException("Failed to read last document id");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -493,8 +499,9 @@ CREATE TABLE IF NOT EXISTS {0} ( {1} VARCHAR(255) PRIMARY KEY, {2} VARCHAR(255)
|
|||||||
var timestamp = doc.date().atStartOfDay(UTC).toInstant().getEpochSecond();
|
var timestamp = doc.date().atStartOfDay(UTC).toInstant().getEpochSecond();
|
||||||
var sender = doc.sender();
|
var sender = doc.sender();
|
||||||
var custom = doc.customer();
|
var custom = doc.customer();
|
||||||
|
var templateId = doc.template() == null ? null : doc.template().id();
|
||||||
var stmt = insertInto(TABLE_DOCUMENTS,TYPE_ID,COMPANY_ID, DATE, DELIVERY_DATE,FOOTER,HEAD, NUMBER, STATE, SENDER,TAX_NUMBER,BANK_ACCOUNT,COURT,CUSTOMER,CUSTOMER_EMAIL,CUSTOMER_NUMBER,CUSTOMER_TAX_NUMBER,TEMPLATE_ID,CURRENCY)
|
var stmt = insertInto(TABLE_DOCUMENTS,TYPE_ID,COMPANY_ID, DATE, DELIVERY_DATE,FOOTER,HEAD, NUMBER, STATE, SENDER,TAX_NUMBER,BANK_ACCOUNT,COURT,CUSTOMER,CUSTOMER_EMAIL,CUSTOMER_NUMBER,CUSTOMER_TAX_NUMBER,TEMPLATE_ID,CURRENCY)
|
||||||
.values(doc.type().id(),doc.companyId(),timestamp,doc.delivery(),doc.footer(),doc.head(),doc.number(),doc.state().code(),sender.name(),sender.taxNumber(),sender.bankAccount(),sender.court(),custom.name(),custom.email(),custom.id(),custom.taxNumber(),doc.template().id(),doc.currency())
|
.values(doc.type().id(),doc.companyId(),timestamp,doc.delivery(),doc.footer(),doc.head(),doc.number(),doc.state().code(),sender.name(),sender.taxNumber(),sender.bankAccount(),sender.court(),custom.name(),custom.email(),custom.id(),custom.taxNumber(),templateId, doc.currency())
|
||||||
.execute(db);
|
.execute(db);
|
||||||
var rs = stmt.getGeneratedKeys();
|
var rs = stmt.getGeneratedKeys();
|
||||||
Long newId = null;
|
Long newId = null;
|
||||||
@@ -589,20 +596,6 @@ CREATE TABLE IF NOT EXISTS {0} ( {1} VARCHAR(255) PRIMARY KEY, {2} VARCHAR(255)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
|
||||||
public void step(CompanySettings settings) {
|
|
||||||
try {
|
|
||||||
update(TABLE_COMPANY_SETTINGS)
|
|
||||||
.set(TYPE_NUMBER)
|
|
||||||
.where(COMPANY_ID,equal(settings.companyId())).where(DOC_TYPE_ID,equal(settings.typeId()))
|
|
||||||
.prepare(db)
|
|
||||||
.apply(settings.typeNumber()+1)
|
|
||||||
.close();
|
|
||||||
} catch (SQLException e) {
|
|
||||||
LOG.log(WARNING,"Failed to increment doc number");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public Pair<Integer> switchPositions(long docId, Pair<Integer> pair) throws UmbrellaException {
|
public Pair<Integer> switchPositions(long docId, Pair<Integer> pair) throws UmbrellaException {
|
||||||
try {
|
try {
|
||||||
@@ -652,6 +645,7 @@ CREATE TABLE IF NOT EXISTS {0} ( {1} VARCHAR(255) PRIMARY KEY, {2} VARCHAR(255)
|
|||||||
var company = rs.getLong(COMPANY_ID);
|
var company = rs.getLong(COMPANY_ID);
|
||||||
var name = rs.getString(NAME);
|
var name = rs.getString(NAME);
|
||||||
var data = rs.getBytes(TEMPLATE);
|
var data = rs.getBytes(TEMPLATE);
|
||||||
|
if (id == 0) return new Template(0,company,"",null);
|
||||||
return new Template(id,company,name,data);
|
return new Template(id,company,name,data);
|
||||||
} catch (SQLException ignored){
|
} catch (SQLException ignored){
|
||||||
return null;
|
return null;
|
||||||
|
|||||||
@@ -1,33 +0,0 @@
|
|||||||
/* © SRSoftware 2025 */
|
|
||||||
package de.srsoftware.umbrella.documents.model;
|
|
||||||
|
|
||||||
import static de.srsoftware.tools.Optionals.emptyIfNull;
|
|
||||||
import static de.srsoftware.umbrella.core.Constants.*;
|
|
||||||
import static de.srsoftware.umbrella.core.Field.*;
|
|
||||||
import static de.srsoftware.umbrella.core.Field.COMPANY_ID;
|
|
||||||
import static de.srsoftware.umbrella.documents.Constants.*;
|
|
||||||
|
|
||||||
import java.sql.ResultSet;
|
|
||||||
import java.sql.SQLException;
|
|
||||||
import java.util.Optional;
|
|
||||||
|
|
||||||
public record CompanySettings(long companyId, long typeId, String typePrefix, String typeSuffix, long typeNumber) {
|
|
||||||
|
|
||||||
public String nextDocId(){
|
|
||||||
return typePrefix+typeNumber+typeSuffix;
|
|
||||||
}
|
|
||||||
|
|
||||||
public static CompanySettings of(ResultSet rs) throws SQLException {
|
|
||||||
var companyId = rs.getLong(COMPANY_ID);
|
|
||||||
var typeId = rs.getLong(DOC_TYPE_ID);
|
|
||||||
var typePrefix = emptyIfNull(rs.getString(TYPE_PREFIX));
|
|
||||||
var typeSuffix = emptyIfNull(rs.getString(TYPE_SUFFIX));
|
|
||||||
var typeNumber = rs.getLong(TYPE_NUMBER);
|
|
||||||
return new CompanySettings(companyId,typeId,typePrefix,typeSuffix,typeNumber);
|
|
||||||
}
|
|
||||||
|
|
||||||
public Optional<CompanySettings> previous(){
|
|
||||||
if (typeNumber<1) return Optional.empty();
|
|
||||||
return Optional.of(new CompanySettings(companyId,typeId,typePrefix,typeSuffix,typeNumber-1));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -45,8 +45,7 @@
|
|||||||
description : description,
|
description : description,
|
||||||
amount : 1,
|
amount : 1,
|
||||||
unit : t('pieces'),
|
unit : t('pieces'),
|
||||||
unit_price : unit_price,
|
unit_price : unit_price
|
||||||
tax : 0
|
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -1,8 +1,8 @@
|
|||||||
<script>
|
<script>
|
||||||
import {onMount} from 'svelte';
|
import {onMount} from 'svelte';
|
||||||
|
|
||||||
import {api} from '../../urls.svelte.js';
|
import {api, post} from '../../urls.svelte.js';
|
||||||
import {t} from '../../translations.svelte.js';
|
import {t} from '../../translations.svelte.js';
|
||||||
|
|
||||||
let {
|
let {
|
||||||
caption,
|
caption,
|
||||||
@@ -16,11 +16,7 @@
|
|||||||
|
|
||||||
async function loadTemplates(){
|
async function loadTemplates(){
|
||||||
const url = api('document/templates');
|
const url = api('document/templates');
|
||||||
var resp = await fetch(url,{
|
var resp = await post(url,{company:company});
|
||||||
credentials : 'include',
|
|
||||||
method : 'POST',
|
|
||||||
body : JSON.stringify({company:company})
|
|
||||||
});
|
|
||||||
if (resp.ok){
|
if (resp.ok){
|
||||||
templates = await resp.json();
|
templates = await resp.json();
|
||||||
} else {
|
} else {
|
||||||
|
|||||||
@@ -2,7 +2,7 @@
|
|||||||
import { onMount } from 'svelte';
|
import { onMount } from 'svelte';
|
||||||
import { useTinyRouter } from 'svelte-tiny-router';
|
import { useTinyRouter } from 'svelte-tiny-router';
|
||||||
|
|
||||||
import {api} from '../../urls.svelte.js';
|
import { api, post } from '../../urls.svelte.js';
|
||||||
import { error, yikes } from '../../warn.svelte';
|
import { error, yikes } from '../../warn.svelte';
|
||||||
import { t } from '../../translations.svelte.js';
|
import { t } from '../../translations.svelte.js';
|
||||||
import { user } from '../../user.svelte.js';
|
import { user } from '../../user.svelte.js';
|
||||||
@@ -29,11 +29,7 @@
|
|||||||
|
|
||||||
async function addPosition(selected){
|
async function addPosition(selected){
|
||||||
const url = api(`document/${doc.id}/position`);
|
const url = api(`document/${doc.id}/position`);
|
||||||
const resp = await fetch(url,{
|
const resp = await post(url,selected);
|
||||||
method : 'POST',
|
|
||||||
credentials : 'include',
|
|
||||||
body : JSON.stringify(selected)
|
|
||||||
});
|
|
||||||
if (resp.ok){
|
if (resp.ok){
|
||||||
doc.positions = await resp.json();
|
doc.positions = await resp.json();
|
||||||
yikes();
|
yikes();
|
||||||
|
|||||||
@@ -204,6 +204,7 @@
|
|||||||
"permission_owner": "Besitzer",
|
"permission_owner": "Besitzer",
|
||||||
"permission_read_only": "lesen",
|
"permission_read_only": "lesen",
|
||||||
"phone": "Telefon",
|
"phone": "Telefon",
|
||||||
|
"pieces": "Stück",
|
||||||
"pos": "Pos",
|
"pos": "Pos",
|
||||||
"position": "Position",
|
"position": "Position",
|
||||||
"positions": "Positionen",
|
"positions": "Positionen",
|
||||||
|
|||||||
@@ -204,6 +204,7 @@
|
|||||||
"permission_owner": "owner",
|
"permission_owner": "owner",
|
||||||
"permission_read_only": "read-only",
|
"permission_read_only": "read-only",
|
||||||
"phone": "phone",
|
"phone": "phone",
|
||||||
|
"pieces": "pieces",
|
||||||
"pos": "pos",
|
"pos": "pos",
|
||||||
"position": "position",
|
"position": "position",
|
||||||
"positions": "positions",
|
"positions": "positions",
|
||||||
|
|||||||
Reference in New Issue
Block a user