src/frames/frame-comr.ts   A
last analyzed

Complexity

Total Complexity 9
Complexity/F 0

Size

Lines of Code 88
Function Count 0

Duplication

Duplicated Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
wmc 9
eloc 68
mnd 9
bc 9
fnc 0
dl 0
loc 88
rs 10
bpm 0
cpm 0
noi 0
c 0
b 0
f 0
1
import { TextEncoding } from '../definitions/Encoding'
2
import { FrameBuilder } from "../FrameBuilder"
3
import { FrameReader } from "../FrameReader"
4
import { CommercialFrame } from '../types/TagFrames'
5
import { validateCurrencyCode } from './util'
6
import { retrievePictureAndMimeType } from './util-picture'
7
8
const toZeroPaddedString = (value: number, width: number) =>
9
    value.toString().padStart(width, '0').substring(0, width)
10
11
export const COMR = {
12
    create: (comr: CommercialFrame): Buffer => {
13
        const builder = new FrameBuilder("COMR", TextEncoding.UTF_16_WITH_BOM)
14
15
        // Price string
16
        const priceString =
17
            Object
18
                .entries(comr.prices || {})
19
                .map(
20
                    ([currencyCode, price]) =>
21
                        validateCurrencyCode(currencyCode) + price.toString()
22
                )
23
                .join("/")
24
25
        builder
26
            .appendTerminatedText(priceString)
27
            .appendText(
28
                toZeroPaddedString(comr.validUntil.year, 4) +
29
                toZeroPaddedString(comr.validUntil.month, 2) +
30
                toZeroPaddedString(comr.validUntil.day, 2)
31
            )
32
            .appendTerminatedText(comr.contactUrl ?? "")
33
            .appendNumber(comr.receivedAs, {size: 1})
34
            .appendTerminatedTextWithFrameEncoding(comr.nameOfSeller ?? "")
35
            .appendTerminatedTextWithFrameEncoding(comr.description ?? "")
36
37
        // Seller logo
38
        if (comr.sellerLogo) {
39
            const { pictureBuffer, mimeType } = retrievePictureAndMimeType({
40
                filenameOrBuffer: comr.sellerLogo.picture,
41
                mimeType: comr.sellerLogo.mimeType
42
            })
43
            builder.appendTerminatedText(mimeType)
44
            builder.appendBuffer(pictureBuffer)
45
        }
46
        return builder.getBufferWithPartialHeader()
47
    },
48
49
    read: (buffer: Buffer): CommercialFrame => {
50
        const reader = new FrameReader(buffer, {consumeEncodingByte: true})
51
52
        const prices = reader.consumeTerminatedText()
53
            .split('/')
54
            .filter((price) => price.length > 3)
55
            .reduce<Record<string, string | number>>(
56
                (prices, price) => (
57
                    prices[price.substring(0, 3)] = price.substring(3),
58
                    prices
59
                ),
60
                {}
61
            )
62
63
        // Valid until
64
        const validUntilString = reader.consumeText({size: 8})
65
        const validUntil = { year: 0, month: 0, day: 0 }
66
        if(/^\d+$/.test(validUntilString)) {
67
            validUntil.year = parseInt(validUntilString.substring(0, 4))
68
            validUntil.month = parseInt(validUntilString.substring(4, 6))
69
            validUntil.day = parseInt(validUntilString.substring(6))
70
        }
71
72
        return {
73
            prices,
74
            validUntil,
75
            contactUrl: reader.consumeTerminatedText(),
76
            receivedAs: reader.consumeNumber({size: 1}),
77
            nameOfSeller: reader.consumeTerminatedTextWithFrameEncoding(),
78
            description: reader.consumeTerminatedTextWithFrameEncoding(),
79
            ...(reader.isBufferEmpty() ? {} : {
80
                sellerLogo: {
81
                    mimeType: reader.consumeTerminatedText(),
82
                    picture: reader.consumePossiblyEmptyBuffer()
83
                }
84
            })
85
        }
86
    }
87
}
88