JSPM

  • ESM via JSPM
  • ES Module Entrypoint
  • Export Map
  • Keywords
  • License
  • Repository URL
  • TypeScript Types
  • README
  • Created
  • Published
  • Downloads 14
  • Score
    100M100P100Q52932F
  • License MIT

Provides functionality around generating invoices.

Package Exports

  • lbx-invoice
  • lbx-invoice/dist/index.js

This package does not declare an exports field, so the exports above have been automatically detected and optimized by JSPM instead. If any package subpath is missing, it is recommended to post an issue to the original package (lbx-invoice) to support the "exports" field. If that is not possible, create a JSPM override to customize the exports field for this package.

Readme

lbx-invoice

This packages aims to take care of most of your invoicing concerns, including:

  • Generation of continuous invoice numbers by saving the amount of created invoices through one year
  • Generation of invoice pdf files in the format PDF-A from a invoice model instance

This library was built with customization in mind, so most things can easily be modified.

Usage

Register the component

The minimum required code changes to use the library to its full extend is simply registering it in the application.ts:

import { BaseInvoiceRepository, LbxInvoiceComponent, NumberInvoicesRepository } from 'lbx-invoice';

export class MyApplication extends BootMixin(ServiceMixin(RepositoryMixin(RestApplication))) {
    constructor(options: ApplicationConfig = {}) {
        // ...
        this.component(LbxInvoiceComponent);
        this.repository(BaseInvoiceRepository);
        this.repository(NumberInvoicesRepository);
        // ...
    }
}

If you don't want to use the predefined repositories you can create your own and bind them to the corresponding key in LbxInvoiceBindings.

Almost everything above comes from the library out of the box. You only need to create your own PdfService for generating the files.

Create your own PdfService

import { BaseCompanyInfo, BaseInvoice, BasePdfService } from 'lbx-invoice';

const invoicePath: string = path.join(__dirname, '..', '../src/services/invoices');

@injectable({ scope: BindingScope.TRANSIENT })
export class InvoicePdfService extends BasePdfService<BaseInvoice, BaseCompanyInfo> {
    protected readonly TAX_OFFICE?: string = undefined;
    protected readonly TAX_NUMBER?: string = undefined;
    protected readonly IBAN?: string = undefined;
    protected readonly BIC?: string = undefined;
    protected readonly BANK_NAME?: string = undefined;
    protected readonly BANK_CODE?: string = undefined;
    protected readonly BANK_ACCOUNT_NUMBER?: string = undefined;
    protected readonly companyInfo: BaseCompanyInfo = {
        name: 'Example Company',
        fullName: 'Example Company LLC',
        email: 'info@example-company.com',
        phone: '12345 67890123',
        address: {
            street: 'Example street',
            number: '1b',
            postcode: '12345',
            city: 'Example city'
        }
    };

    protected async handleFinishedInvoicePdf(pdfData: string, invoice: BaseInvoice): Promise<void> {
        writeFileSync(path.join(invoicePath, `${invoice.number}.pdf`), pdfData, 'base64');
    }
}

Enjoy!

That's it, now you can use it inside your code:

import { BaseInvoice, BaseInvoiceRepository, InvoiceNumberService, LbxInvoiceBindings } from 'lbx-invoice';
// ...
export class ExampleInvoiceController {
    constructor(
        @inject(LbxInvoiceBindings.INVOICE_REPOSITORY)
        private readonly baseInvoiceRepository: BaseInvoiceRepository,
        @service(InvoicePdfService)
        private readonly pdfService: InvoicePdfService,
        @inject(LbxInvoiceBindings.INVOICE_NUMBER_SERVICE)
        private readonly invoiceNumberService: InvoiceNumberService,
        @inject('datasources.db')
        private readonly dataSource: DbDataSource
    ) {}

    @post('/invoices')
    async create(
        @requestBody({
            content: {
                'application/json': {
                    schema: getModelSchemaRef(BaseInvoice, {
                        exclude: ['id', 'number']
                    })
                }
            }
        })
        invoice: Omit<BaseInvoice, 'id'>
    ): Promise<void> {
        const transaction: juggler.Transaction = await this.dataSource.beginTransaction(IsolationLevel.READ_COMMITTED);
        try {
            invoice.number = await this.invoiceNumberService.generateInvoiceNumber(invoice.customerAddressData, transaction);
            const finishedInvoice: BaseInvoice = await this.baseInvoiceRepository.create(invoice, { transaction: transaction });
            await this.pdfService.createInvoicePdf(finishedInvoice);
            await transaction.commit();
        }
        catch (error) {
            await transaction.rollback();
            throw error;
        }
    }
}

Customization

The library is highly customizable through the usage of Bindings.

Almost everything can be overriden by you when you provide a value for the specific Binding:

import { LbxInvoiceBindings } from 'lbx-invoice';
// ...
this.bind(LbxInvoiceBindings.INVOICE_REPOSITORY).toClass(MyCustomInvoiceRepository);
// ...

All bindings can be accessed under LbxInvoiceBindings.