Compare commits
506 Commits
ts-runQuer
...
stable
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
65c0a5a316 | ||
|
|
b0deedb411 | ||
|
|
103d95bbc8 | ||
|
|
d11fc59ec9 | ||
|
|
1c931cf01c | ||
|
|
7f50c73866 | ||
|
|
a7cde1f90d | ||
|
|
398ada0afd | ||
|
|
8b928b3b21 | ||
|
|
3897a5a51c | ||
|
|
94f94497af | ||
|
|
a72fd74c5e | ||
|
|
5214549ed3 | ||
|
|
3c8212e130 | ||
|
|
eface19216 | ||
|
|
f413fa03ae | ||
|
|
81b30d74e4 | ||
|
|
0fddcac76d | ||
|
|
1511587e88 | ||
|
|
ff7c358b83 | ||
|
|
f88b00ae77 | ||
|
|
f5a1293e3c | ||
|
|
5a79beadfa | ||
|
|
6e934e46a8 | ||
|
|
18423a3167 | ||
|
|
c1a70377b9 | ||
|
|
dd4b891fd9 | ||
|
|
89a92ecbbe | ||
|
|
bde99b75ae | ||
|
|
8d3b046bef | ||
|
|
f7f58847dc | ||
|
|
23752f1da9 | ||
|
|
1cc2da1de3 | ||
|
|
04b5bdc62f | ||
|
|
fc78d5b546 | ||
|
|
f5586501bf | ||
|
|
d902c38253 | ||
|
|
a085945898 | ||
|
|
def06693ab | ||
|
|
bf72a26e5c | ||
|
|
10c35e18d3 | ||
|
|
aea6e79402 | ||
|
|
81db7399da | ||
|
|
7c9a499f91 | ||
|
|
df9e6ec66d | ||
|
|
a4d3f277ea | ||
|
|
cab24df3ce | ||
|
|
c92e445416 | ||
|
|
e86cbcdbb3 | ||
|
|
3a14d46a05 | ||
|
|
14c1d9f03b | ||
|
|
1884a188b7 | ||
|
|
c471c8908b | ||
|
|
7a252d0694 | ||
|
|
3b6c97faab | ||
|
|
bc09c0412c | ||
|
|
87779d3199 | ||
|
|
e5eb8646c2 | ||
|
|
0504becaf5 | ||
|
|
04f8140d26 | ||
|
|
9fd004205c | ||
|
|
f90fc69341 | ||
|
|
7e1c0a8682 | ||
|
|
454f019f7a | ||
|
|
f1a4c888b2 | ||
|
|
524707cecc | ||
|
|
8351edc8bb | ||
|
|
4957cd652b | ||
|
|
ad58561f4e | ||
|
|
dbdc5af2b9 | ||
|
|
679b94a626 | ||
|
|
5e217ec9a2 | ||
|
|
52ce2a179e | ||
|
|
be1c194eb4 | ||
|
|
7d9190ea9c | ||
|
|
c883e71e49 | ||
|
|
6710456c05 | ||
|
|
be2126e136 | ||
|
|
ac08b87273 | ||
|
|
7ddd79c61e | ||
|
|
4ee70e7f1f | ||
|
|
7faecf4273 | ||
|
|
ce99c49ddb | ||
|
|
c947d964fa | ||
|
|
46aa79ab7c | ||
|
|
af3598ec76 | ||
|
|
83ba751410 | ||
|
|
722e30e385 | ||
|
|
e88bd783f2 | ||
|
|
8c0ca48781 | ||
|
|
5f1fadb7cc | ||
|
|
cac4761982 | ||
|
|
e1a694a554 | ||
|
|
c4ad24edde | ||
|
|
f5b9a5b23d | ||
|
|
8b49a25ab4 | ||
|
|
15298703ac | ||
|
|
7096d00fc6 | ||
|
|
e8b4a750ed | ||
|
|
4a7b0e7365 | ||
|
|
f1da358186 | ||
|
|
a23a28522f | ||
|
|
6a5de96033 | ||
|
|
abeeb05091 | ||
|
|
bd063423e5 | ||
|
|
ca480a8269 | ||
|
|
bdf4dda3a8 | ||
|
|
0c1c8e6adb | ||
|
|
ed91fb1ef4 | ||
|
|
b14c77aed7 | ||
|
|
64df0e107c | ||
|
|
9b59333563 | ||
|
|
b09d800e40 | ||
|
|
d1c3b9bab1 | ||
|
|
663f830cc9 | ||
|
|
0312f516ad | ||
|
|
9dcd22962c | ||
|
|
5ada00cf97 | ||
|
|
0f2226e993 | ||
|
|
5f823156b7 | ||
|
|
c53e9e9e41 | ||
|
|
ecb4d7153c | ||
|
|
45d53ff771 | ||
|
|
205ccfe3d6 | ||
|
|
4bb59fd7f6 | ||
|
|
58f87dc80f | ||
|
|
c017b8a228 | ||
|
|
0637b1d5f8 | ||
|
|
e6ed4505b3 | ||
|
|
215e00ac14 | ||
|
|
1808f51e85 | ||
|
|
0f1c231d37 | ||
|
|
95180cc780 | ||
|
|
2005c1b0ac | ||
|
|
2ef397112c | ||
|
|
6c57b4ec9e | ||
|
|
efb50edf9f | ||
|
|
96c37350d5 | ||
|
|
f80eb888a0 | ||
|
|
70f6afbda6 | ||
|
|
0d06bc1f7e | ||
|
|
6281d54a38 | ||
|
|
d637a69ee4 | ||
|
|
645958bbeb | ||
|
|
df958eb35c | ||
|
|
39dbdc0418 | ||
|
|
d3a7b6228a | ||
|
|
484211185b | ||
|
|
8506b87f2c | ||
|
|
69a04a5c21 | ||
|
|
826511779e | ||
|
|
30f21497a6 | ||
|
|
b1bf7ee7cd | ||
|
|
266de169db | ||
|
|
d412590b33 | ||
|
|
635ef27696 | ||
|
|
ed098c4a69 | ||
|
|
b98ff3f50d | ||
|
|
879869c85a | ||
|
|
2cd3c9f8a9 | ||
|
|
81afedb610 | ||
|
|
1c9b43671e | ||
|
|
b5f8aa4d05 | ||
|
|
e659ccf3f4 | ||
|
|
603f970f12 | ||
|
|
c9e6d7897b | ||
|
|
cc347aef08 | ||
|
|
49c5adc9cf | ||
|
|
b8c92b98b8 | ||
|
|
f6f49b1fe7 | ||
|
|
df42cccce7 | ||
|
|
c30981638e | ||
|
|
a8c4c5fa23 | ||
|
|
290c6f646f | ||
|
|
6658dc2197 | ||
|
|
f3385dafa2 | ||
|
|
73f2de1ea6 | ||
|
|
0757f9d680 | ||
|
|
835b6987a7 | ||
|
|
2e70c11c74 | ||
|
|
c01e229bd7 | ||
|
|
e8ff02b2e7 | ||
|
|
b1c8b3d689 | ||
|
|
7b314e3b25 | ||
|
|
f78383be29 | ||
|
|
9ea7bd255a | ||
|
|
fe8532578d | ||
|
|
41b12151f6 | ||
|
|
d60e7501cc | ||
|
|
0760583359 | ||
|
|
a757ba6bdc | ||
|
|
7a018e09a9 | ||
|
|
c4d01fe63f | ||
|
|
446f40714d | ||
|
|
3b26aa05b5 | ||
|
|
d613a6be6e | ||
|
|
2b37d5a642 | ||
|
|
6a41d28404 | ||
|
|
8d4dbbf5f2 | ||
|
|
b8d2797259 | ||
|
|
8201085ccb | ||
|
|
c16a8faa3f | ||
|
|
4ce7f55e0c | ||
|
|
574448ff3b | ||
|
|
7fcda084ab | ||
|
|
baf04a4d48 | ||
|
|
a879960a2d | ||
|
|
eec5fbb1cc | ||
|
|
b74f0f2982 | ||
|
|
12f4295932 | ||
|
|
d33e5cc766 | ||
|
|
df3aaf961d | ||
|
|
6b57e45e04 | ||
|
|
842e11b3a1 | ||
|
|
e3101fb86b | ||
|
|
943f903646 | ||
|
|
b4a620e74e | ||
|
|
d3d9f70657 | ||
|
|
c19cc56c55 | ||
|
|
40e432dedb | ||
|
|
7824c52d9f | ||
|
|
145659b256 | ||
|
|
7e84cf897c | ||
|
|
3661c1585e | ||
|
|
17cdea9beb | ||
|
|
228f38617b | ||
|
|
74ade73476 | ||
|
|
81acd29c73 | ||
|
|
1da9c821ee | ||
|
|
2006d885b8 | ||
|
|
167522d322 | ||
|
|
f5307e4bd4 | ||
|
|
382d347508 | ||
|
|
c792c0f54e | ||
|
|
73d0f04d45 | ||
|
|
925926f542 | ||
|
|
44ddf210ea | ||
|
|
62c6a8775c | ||
|
|
1af5ab09e9 | ||
|
|
aa22e6951d | ||
|
|
55724acafa | ||
|
|
e3934b96dc | ||
|
|
2221fd8dff | ||
|
|
db6b4e4800 | ||
|
|
abd049e715 | ||
|
|
c51e636637 | ||
|
|
3a486ed973 | ||
|
|
33c204dedb | ||
|
|
41a34d0f1c | ||
|
|
f1488077dd | ||
|
|
c0b21a9f7e | ||
|
|
4ae654d54d | ||
|
|
1bbba663b2 | ||
|
|
44c7b4eab0 | ||
|
|
ae0faf467f | ||
|
|
a5a5f30dd7 | ||
|
|
f06bbf9a51 | ||
|
|
1c61508abb | ||
|
|
deec1f998c | ||
|
|
bf404104c2 | ||
|
|
5fde6561d0 | ||
|
|
6e9eddeb56 | ||
|
|
b926af286a | ||
|
|
f43097f813 | ||
|
|
04147fb9b9 | ||
|
|
cd4a2b6678 | ||
|
|
16faf49438 | ||
|
|
13a39168c4 | ||
|
|
10d53fbe5f | ||
|
|
21c65cf68f | ||
|
|
e7f6348d9a | ||
|
|
af6de6b585 | ||
|
|
d8c7a0a358 | ||
|
|
58f7b09e8d | ||
|
|
7b36c2207a | ||
|
|
6de1fe34e3 | ||
|
|
ff073b1221 | ||
|
|
1d4eaaa79c | ||
|
|
3b83f064d4 | ||
|
|
c330020487 | ||
|
|
2f7b3917ed | ||
|
|
933fc27126 | ||
|
|
c910b6efcb | ||
|
|
633463a184 | ||
|
|
5ac4c58d1e | ||
|
|
f93893e007 | ||
|
|
42699ac044 | ||
|
|
bb07652cf8 | ||
|
|
dc47c6d72a | ||
|
|
4b12561905 | ||
|
|
ca4ea97768 | ||
|
|
87813b398a | ||
|
|
7865e08c91 | ||
|
|
e116d01453 | ||
|
|
a6c1443669 | ||
|
|
de604b9f3a | ||
|
|
1f79708ea3 | ||
|
|
494d67459f | ||
|
|
9e7c2e7a65 | ||
|
|
1f5ff932b1 | ||
|
|
75af7b9987 | ||
|
|
b8fbc9b19c | ||
|
|
fc643d28c6 | ||
|
|
9d6b9c556d | ||
|
|
46dbc89482 | ||
|
|
bde303ec45 | ||
|
|
6512c465f0 | ||
|
|
6f216cc1aa | ||
|
|
ad65fcdffc | ||
|
|
87747a83b9 | ||
|
|
0501deac2d | ||
|
|
95c7d5bc2c | ||
|
|
09380db661 | ||
|
|
52c1676005 | ||
|
|
9c9f6645d3 | ||
|
|
9102d974a5 | ||
|
|
7cef3fe24b | ||
|
|
496d60c3a7 | ||
|
|
ce8d53a513 | ||
|
|
20c2f1950b | ||
|
|
723d9cd62c | ||
|
|
1de788ea68 | ||
|
|
354152dbb5 | ||
|
|
c2ee92878c | ||
|
|
8237eb56ab | ||
|
|
28e0d712ab | ||
|
|
debb33a63d | ||
|
|
5252f45073 | ||
|
|
5954141c15 | ||
|
|
ca27949989 | ||
|
|
8ac74ed397 | ||
|
|
7c8e9bb5ec | ||
|
|
d1ff06840e | ||
|
|
c2c8c1719e | ||
|
|
5d36ecbbbb | ||
|
|
9169bfabad | ||
|
|
fb6dc5e8f1 | ||
|
|
d60bb6a19e | ||
|
|
996f238648 | ||
|
|
7c744f0e3d | ||
|
|
2f54a948be | ||
|
|
652d75a939 | ||
|
|
104c9803f7 | ||
|
|
bc93604576 | ||
|
|
a1af1ff3d2 | ||
|
|
47d77a3198 | ||
|
|
82b4643c78 | ||
|
|
0096907368 | ||
|
|
1504127979 | ||
|
|
6f7306cd37 | ||
|
|
063d468836 | ||
|
|
7e88de182e | ||
|
|
bf4319d978 | ||
|
|
c3d89b6509 | ||
|
|
cb731099e6 | ||
|
|
b6073f7e6f | ||
|
|
9b2d74c3ad | ||
|
|
7713848067 | ||
|
|
c8a901d3ff | ||
|
|
d02e1b3640 | ||
|
|
19dbf815e6 | ||
|
|
df70a791fd | ||
|
|
a84036e0c6 | ||
|
|
973070f22b | ||
|
|
5f0df5ed53 | ||
|
|
80be279e11 | ||
|
|
1aaafbf435 | ||
|
|
1dd1283d56 | ||
|
|
184ec5f1c0 | ||
|
|
56e5c33c3e | ||
|
|
37c5278abf | ||
|
|
d1482e38fe | ||
|
|
1cce6137a0 | ||
|
|
27ea0ddd98 | ||
|
|
bd7992a45a | ||
|
|
95a0769eaa | ||
|
|
af9713d5b1 | ||
|
|
ab9f771829 | ||
|
|
fa0c91b22c | ||
|
|
2e5f5b48fa | ||
|
|
a52ae2dba1 | ||
|
|
19cd163b30 | ||
|
|
06b687e899 | ||
|
|
fa42c2202e | ||
|
|
0537544de2 | ||
|
|
be1c119799 | ||
|
|
76f398dd16 | ||
|
|
064d3e5dbb | ||
|
|
c6c3243234 | ||
|
|
60b183b094 | ||
|
|
9b5fb43ad3 | ||
|
|
7c58261b72 | ||
|
|
712ca71656 | ||
|
|
c8ad8a693b | ||
|
|
1be74096f6 | ||
|
|
92b4eec36a | ||
|
|
44038fbdce | ||
|
|
b4c7996d1a | ||
|
|
39fd8a5457 | ||
|
|
24da9b7b5a | ||
|
|
3edb8db94b | ||
|
|
909b4b1c0b | ||
|
|
38f2ab252e | ||
|
|
f0772b147f | ||
|
|
9fc9d5c642 | ||
|
|
73db82042c | ||
|
|
a14f558258 | ||
|
|
97081d46c4 | ||
|
|
60f83b334e | ||
|
|
340ac869ce | ||
|
|
b2b6ba4921 | ||
|
|
3274a06e34 | ||
|
|
e9850bfc56 | ||
|
|
529c42cccf | ||
|
|
2a00227486 | ||
|
|
5252edbf70 | ||
|
|
74c15b4f42 | ||
|
|
d482b9baf6 | ||
|
|
cde216523e | ||
|
|
8aeb815b5a | ||
|
|
3c602268e3 | ||
|
|
9177fb4d77 | ||
|
|
e3f1fafad9 | ||
|
|
32bf923c1a | ||
|
|
d3a0e8067e | ||
|
|
105d5007cf | ||
|
|
bafa486668 | ||
|
|
80a2b34d43 | ||
|
|
a5e1e38e74 | ||
|
|
0486e9e37b | ||
|
|
09722d8678 | ||
|
|
cd22e38660 | ||
|
|
f83fe76280 | ||
|
|
b9e1e6030f | ||
|
|
4874b53c7c | ||
|
|
b1a48f4f27 | ||
|
|
3fee9cbb42 | ||
|
|
a2a460a883 | ||
|
|
6bcd67a906 | ||
|
|
9e2d253fb6 | ||
|
|
a7efc82944 | ||
|
|
25f4bb5557 | ||
|
|
74d6b7edc5 | ||
|
|
1204b5b1a6 | ||
|
|
59ddc965ec | ||
|
|
9cc4ffaf33 | ||
|
|
11ba63d086 | ||
|
|
06d2aba57c | ||
|
|
7ecaad529f | ||
|
|
5ef3aa4153 | ||
|
|
5e83e14637 | ||
|
|
8dbc10efd7 | ||
|
|
592f0540f9 | ||
|
|
0e28f77a1f | ||
|
|
618609dbfa | ||
|
|
c86f1f5546 | ||
|
|
a09a028dc9 | ||
|
|
44da71bcdd | ||
|
|
343ea0c306 | ||
|
|
a60f22ef5c | ||
|
|
d614070f44 | ||
|
|
fd5d81e399 | ||
|
|
841d3ac115 | ||
|
|
3df101a91d | ||
|
|
3124c29052 | ||
|
|
a4a4eda0eb | ||
|
|
7d418b91b4 | ||
|
|
9ef7771adc | ||
|
|
d0a8b678d3 | ||
|
|
6d52cc7c73 | ||
|
|
2acc034fc1 | ||
|
|
51a2cb91f2 | ||
|
|
44d045f546 | ||
|
|
6be206ff28 | ||
|
|
c4badb9daf | ||
|
|
f8ad766695 | ||
|
|
a55d4634b1 | ||
|
|
42bc4c8acb | ||
|
|
efd273bfa5 | ||
|
|
3fb71b74cd | ||
|
|
2bb3e3ea48 | ||
|
|
59ec877ddd | ||
|
|
31e9025df3 | ||
|
|
1b42bc0e75 | ||
|
|
0ad3f12686 | ||
|
|
6de775a1bf | ||
|
|
1d74b9d782 | ||
|
|
933a5f5e7c | ||
|
|
cd280802de | ||
|
|
b53a4e5bf8 | ||
|
|
c20648c33a | ||
|
|
fa32948508 | ||
|
|
9ec349e733 | ||
|
|
4fa2bf1b29 | ||
|
|
3d01a76296 | ||
|
|
f9c0539d68 | ||
|
|
dde1495854 | ||
|
|
065f87c2e8 | ||
|
|
c049cf440f | ||
|
|
1149730962 | ||
|
|
16de8cb91b | ||
|
|
caec05df14 | ||
|
|
e387f4ca1c | ||
|
|
6d7ffe6a25 | ||
|
|
ad0c0f6865 | ||
|
|
dd541e5f70 |
30
.github/actions/bump-package-versions
vendored
Executable file
@@ -0,0 +1,30 @@
|
||||
#!/bin/bash
|
||||
set -euo pipefail
|
||||
|
||||
if [ "$#" -gt 0 ]; then
|
||||
version="${1#v}"
|
||||
else
|
||||
version=""
|
||||
fi
|
||||
|
||||
files_to_bump=(
|
||||
packages/api/package.json
|
||||
packages/desktop-client/package.json
|
||||
packages/desktop-electron/package.json
|
||||
)
|
||||
|
||||
for file in "${files_to_bump[@]}"; do
|
||||
if [ -z "$version" ]; then
|
||||
# version format: YY.MM.patch
|
||||
# logic: if before the 25th, bump patch, else set minor/major to next month
|
||||
version="$(jq -r .version "$file" | perl -e '($y,$m,$p)=split/\./,<>;$d=(localtime)[3];$d>25?($p=0,++$m,$m>12&&($m=1,++$y)):$p++;print"$y.$m.$p\n"')"
|
||||
if [ -z "$version" ]; then
|
||||
echo "Error: Failed to calculate new version" >&2
|
||||
exit 1
|
||||
fi
|
||||
fi
|
||||
|
||||
echo "Bumping $file to version $version"
|
||||
jq '.version = "'"$version"'"' "$file" > "$file.tmp"
|
||||
mv "$file.tmp" "$file"
|
||||
done
|
||||
14
.github/workflows/build.yml
vendored
@@ -68,3 +68,17 @@ jobs:
|
||||
with:
|
||||
name: build-stats
|
||||
path: packages/desktop-client/build-stats
|
||||
|
||||
server:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
- name: Set up environment
|
||||
uses: ./.github/actions/setup
|
||||
- name: Build Server
|
||||
run: cd packages/sync-server && yarn build
|
||||
- name: Upload Build
|
||||
uses: actions/upload-artifact@v4
|
||||
with:
|
||||
name: sync-server
|
||||
path: packages/sync-server/build
|
||||
|
||||
90
.github/workflows/docker-edge.yml
vendored
Normal file
@@ -0,0 +1,90 @@
|
||||
name: Build Edge Docker Image
|
||||
|
||||
# Edge Docker images are built for every commit, and daily
|
||||
on:
|
||||
push:
|
||||
branches:
|
||||
- master
|
||||
paths:
|
||||
- 'packages/sync-server/**'
|
||||
pull_request:
|
||||
branches:
|
||||
- master
|
||||
paths:
|
||||
- 'packages/sync-server/**'
|
||||
schedule:
|
||||
- cron: '0 0 * * *'
|
||||
workflow_dispatch:
|
||||
|
||||
permissions:
|
||||
contents: read
|
||||
packages: write
|
||||
|
||||
env:
|
||||
IMAGES: |
|
||||
actualbudget/actual-server
|
||||
ghcr.io/actualbudget/actual-server
|
||||
ghcr.io/actualbudget/actual
|
||||
|
||||
# Creates the following tags:
|
||||
# - actual-server:edge
|
||||
TAGS: |
|
||||
type=edge,value=edge
|
||||
type=sha
|
||||
|
||||
jobs:
|
||||
build:
|
||||
if: ${{ github.event.repository.fork == false }}
|
||||
name: Build Docker image
|
||||
runs-on: ubuntu-latest
|
||||
strategy:
|
||||
matrix:
|
||||
os: [ubuntu, alpine]
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Set up QEMU
|
||||
uses: docker/setup-qemu-action@v3
|
||||
|
||||
- name: Set up Docker Buildx
|
||||
uses: docker/setup-buildx-action@v3
|
||||
|
||||
- name: Docker meta
|
||||
id: meta
|
||||
uses: docker/metadata-action@v5
|
||||
with:
|
||||
# Push to both Docker Hub and Github Container Registry
|
||||
images: ${{ env.IMAGES }}
|
||||
flavor: ${{ matrix.os != 'ubuntu' && format('suffix=-{0}', matrix.os) || '' }}
|
||||
tags: ${{ env.TAGS }}
|
||||
|
||||
- name: Login to Docker Hub
|
||||
uses: docker/login-action@v3
|
||||
if: github.event_name != 'pull_request'
|
||||
with:
|
||||
username: ${{ secrets.DOCKERHUB_USERNAME }}
|
||||
password: ${{ secrets.DOCKERHUB_TOKEN }}
|
||||
|
||||
- name: Login to GitHub Container Registry
|
||||
uses: docker/login-action@v3
|
||||
if: github.event_name != 'pull_request'
|
||||
with:
|
||||
registry: ghcr.io
|
||||
username: ${{ github.repository_owner }}
|
||||
password: ${{ secrets.GITHUB_TOKEN }}
|
||||
|
||||
- name: Download artifacts
|
||||
run: ./packages/sync-server/docker/download-artifacts.sh
|
||||
env:
|
||||
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
||||
|
||||
- name: Build and push image
|
||||
uses: docker/build-push-action@v5
|
||||
with:
|
||||
context: .
|
||||
push: ${{ github.event_name != 'pull_request' }}
|
||||
file: packages/sync-server/docker/edge-${{ matrix.os }}.Dockerfile
|
||||
platforms: linux/amd64,linux/arm64,linux/arm/v7${{ matrix.os == 'alpine' && ',linux/arm/v6' || '' }}
|
||||
tags: ${{ steps.meta.outputs.tags }}
|
||||
build-args: |
|
||||
GITHUB_TOKEN=${{ secrets.GITHUB_TOKEN }}
|
||||
89
.github/workflows/docker-release.yml
vendored
Normal file
@@ -0,0 +1,89 @@
|
||||
name: Build Stable Docker Image
|
||||
|
||||
# Stable Docker images are built for every new tag
|
||||
on:
|
||||
push:
|
||||
tags:
|
||||
- 'v*.*.*'
|
||||
paths-ignore:
|
||||
- README.md
|
||||
- LICENSE.txt
|
||||
|
||||
env:
|
||||
IMAGES: |
|
||||
actualbudget/actual-server
|
||||
ghcr.io/actualbudget/actual-server
|
||||
ghcr.io/actualbudget/actual
|
||||
|
||||
# Creates the following tags:
|
||||
# - actual-server:latest (see docker/metadata-action flavor inputs, below)
|
||||
# - actual-server:1.3
|
||||
# - actual-server:1.3.7
|
||||
# - actual-server:sha-90dd603
|
||||
TAGS: |
|
||||
type=semver,pattern={{version}}
|
||||
|
||||
jobs:
|
||||
build:
|
||||
name: Build Docker image
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
|
||||
- name: Set up QEMU
|
||||
uses: docker/setup-qemu-action@v3
|
||||
|
||||
- name: Set up Docker Buildx
|
||||
uses: docker/setup-buildx-action@v3
|
||||
|
||||
- name: Docker meta
|
||||
id: meta
|
||||
uses: docker/metadata-action@v5
|
||||
with:
|
||||
# Push to both Docker Hub and Github Container Registry
|
||||
images: ${{ env.IMAGES }}
|
||||
# Automatically update :latest
|
||||
flavor: latest=true
|
||||
tags: ${{ env.TAGS }}
|
||||
|
||||
- name: Docker meta for Alpine image
|
||||
id: alpine-meta
|
||||
uses: docker/metadata-action@v5
|
||||
with:
|
||||
images: ${{ env.IMAGES }}
|
||||
# Automatically update :latest
|
||||
flavor: |
|
||||
latest=true
|
||||
suffix=-alpine,onlatest=true
|
||||
tags: ${{ env.TAGS }}
|
||||
|
||||
- name: Login to Docker Hub
|
||||
uses: docker/login-action@v3
|
||||
with:
|
||||
username: ${{ secrets.DOCKERHUB_USERNAME }}
|
||||
password: ${{ secrets.DOCKERHUB_TOKEN }}
|
||||
|
||||
- name: Login to GitHub Container Registry
|
||||
uses: docker/login-action@v3
|
||||
with:
|
||||
registry: ghcr.io
|
||||
username: ${{ github.repository_owner }}
|
||||
password: ${{ secrets.GITHUB_TOKEN }}
|
||||
|
||||
- name: Build and push ubuntu image
|
||||
uses: docker/build-push-action@v5
|
||||
with:
|
||||
context: .
|
||||
push: true
|
||||
file: packages/sync-server/docker/stable-ubuntu.Dockerfile
|
||||
platforms: linux/amd64,linux/arm64,linux/arm/v7
|
||||
tags: ${{ steps.meta.outputs.tags }}
|
||||
|
||||
- name: Build and push alpine image
|
||||
uses: docker/build-push-action@v5
|
||||
with:
|
||||
context: .
|
||||
push: true
|
||||
file: packages/sync-server/docker/stable-alpine.Dockerfile
|
||||
platforms: linux/amd64,linux/arm64,linux/arm/v7,linux/arm/v6
|
||||
tags: ${{ steps.alpine-meta.outputs.tags }}
|
||||
3
.github/workflows/e2e-test.yml
vendored
@@ -1,6 +1,7 @@
|
||||
name: E2E Tests
|
||||
|
||||
on: [pull_request]
|
||||
on:
|
||||
pull_request:
|
||||
|
||||
env:
|
||||
GITHUB_PR_NUMBER: ${{github.event.pull_request.number}}
|
||||
|
||||
35
.github/workflows/generate-release-pr.yml
vendored
Normal file
@@ -0,0 +1,35 @@
|
||||
name: Generate release PR
|
||||
|
||||
on:
|
||||
workflow_dispatch:
|
||||
inputs:
|
||||
ref:
|
||||
description: 'Commit or branch to release'
|
||||
required: true
|
||||
default: 'master'
|
||||
version:
|
||||
description: 'Version number for the release (optional)'
|
||||
required: false
|
||||
default: ''
|
||||
|
||||
jobs:
|
||||
generate-release-pr:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- name: Checkout
|
||||
uses: actions/checkout@v4
|
||||
with:
|
||||
ref: ${{ github.event.inputs.ref }}
|
||||
- name: Bump package versions
|
||||
id: bump_package_versions
|
||||
shell: bash
|
||||
run: |
|
||||
.github/actions/bump-package-versions ${{ github.event.inputs.version }}
|
||||
echo "version=$(jq -r .version packages/desktop-client/package.json)" > $GITHUB_OUTPUT
|
||||
- name: Create PR
|
||||
uses: peter-evans/create-pull-request@v7
|
||||
with:
|
||||
commit-message: '🔖 (${{ steps.bump_package_versions.outputs.version }})'
|
||||
title: '🔖 (${{ steps.bump_package_versions.outputs.version }})'
|
||||
body: 'Generated by [generate-release-pr.yml](../tree/master/.github/workflows/generate-release-pr.yml)'
|
||||
branch: 'release/v${{ steps.bump_package_versions.outputs.version }}'
|
||||
3
.github/workflows/size-compare.yml
vendored
@@ -13,6 +13,9 @@ name: Compare Sizes
|
||||
|
||||
on:
|
||||
pull_request_target:
|
||||
paths:
|
||||
- 'packages/**'
|
||||
- '!packages/sync-server/**'
|
||||
|
||||
concurrency:
|
||||
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
|
||||
|
||||
@@ -36,6 +36,16 @@ fi
|
||||
|
||||
yarn workspace loot-core build:node
|
||||
|
||||
# Get translations
|
||||
echo "Updating translations..."
|
||||
if ! [ -d packages/desktop-client/locale ]; then
|
||||
git clone https://github.com/actualbudget/translations packages/desktop-client/locale
|
||||
fi
|
||||
pushd packages/desktop-client/locale > /dev/null
|
||||
git pull
|
||||
popd > /dev/null
|
||||
packages/desktop-client/bin/remove-untranslated-languages
|
||||
|
||||
yarn workspace @actual-app/web build --mode=desktop # electron specific build
|
||||
|
||||
yarn workspace desktop-electron update-client
|
||||
|
||||
@@ -113,7 +113,6 @@ export default [
|
||||
'packages/loot-core/**/node_modules/*',
|
||||
'packages/loot-core/**/lib-dist/*',
|
||||
'packages/loot-core/**/proto/*',
|
||||
'packages/sync-server',
|
||||
'.yarn/*',
|
||||
'.github/*',
|
||||
],
|
||||
@@ -671,7 +670,6 @@ export default [
|
||||
},
|
||||
{
|
||||
files: ['packages/loot-core/src/**/*'],
|
||||
|
||||
rules: {
|
||||
'no-restricted-imports': [
|
||||
'warn',
|
||||
@@ -691,6 +689,10 @@ export default [
|
||||
message:
|
||||
'Please use relative imports in loot-core instead of importing from `loot-core/*`',
|
||||
},
|
||||
{
|
||||
group: ['@actual-app/web/*'],
|
||||
message: 'Please do not import `@actual-app/web` in `loot-core`',
|
||||
},
|
||||
],
|
||||
},
|
||||
],
|
||||
@@ -758,7 +760,7 @@ export default [
|
||||
'packages/desktop-client/src/components/budget/MobileBudget.tsx',
|
||||
'packages/desktop-client/src/components/budget/envelope/HoldMenu.tsx',
|
||||
'packages/desktop-client/src/components/budget/envelope/TransferMenu.tsx',
|
||||
'packages/desktop-client/src/components/common/Menu.tsx',
|
||||
'packages/component-library/src/Menu.tsx',
|
||||
'packages/desktop-client/src/components/FinancesApp.tsx',
|
||||
'packages/desktop-client/src/components/GlobalKeys.ts',
|
||||
'packages/desktop-client/src/components/LoggedInUser.tsx',
|
||||
@@ -788,20 +790,6 @@ export default [
|
||||
'packages/desktop-client/src/components/sidebar/Tools.tsx',
|
||||
'packages/desktop-client/src/components/sort.tsx',
|
||||
'packages/desktop-client/src/components/spreadsheet/useSheetValue.ts',
|
||||
'packages/desktop-client/src/components/table.tsx',
|
||||
'packages/desktop-client/src/components/Titlebar.tsx',
|
||||
'packages/desktop-client/src/components/transactions/MobileTransaction.jsx',
|
||||
'packages/desktop-client/src/components/transactions/SelectedTransactions.jsx',
|
||||
'packages/desktop-client/src/components/transactions/SimpleTransactionsTable.jsx',
|
||||
'packages/desktop-client/src/components/transactions/TransactionList.jsx',
|
||||
'packages/desktop-client/src/components/transactions/TransactionsTable.jsx',
|
||||
'packages/desktop-client/src/components/transactions/TransactionsTable.test.jsx',
|
||||
'packages/desktop-client/src/hooks/useAccounts.ts',
|
||||
'packages/desktop-client/src/hooks/useCategories.ts',
|
||||
'packages/desktop-client/src/hooks/usePayees.ts',
|
||||
'packages/desktop-client/src/hooks/useProperFocus.tsx',
|
||||
'packages/desktop-client/src/hooks/useSelected.tsx',
|
||||
'packages/loot-core/src/client/query-hooks.tsx',
|
||||
],
|
||||
|
||||
rules: {
|
||||
@@ -815,6 +803,7 @@ export default [
|
||||
'**/*.test.ts',
|
||||
'**/*.test.jsx',
|
||||
'**/*.test.tsx',
|
||||
'**/*.spec.js',
|
||||
],
|
||||
|
||||
rules: {
|
||||
@@ -832,4 +821,21 @@ export default [
|
||||
'@typescript-eslint/consistent-type-definitions': ['warn', 'type'],
|
||||
},
|
||||
},
|
||||
{
|
||||
files: ['packages/sync-server/**/*'],
|
||||
// TODO: fix the issues in these files
|
||||
rules: {
|
||||
'import/extensions': 'off',
|
||||
'rulesdir/typography': 'off',
|
||||
},
|
||||
},
|
||||
{
|
||||
files: ['packages/sync-server/src/app-gocardless/banks/*.js'],
|
||||
rules: {
|
||||
'import/no-anonymous-default-export': 'off',
|
||||
'import/no-default-export': 'off',
|
||||
// can be re-enabled after https://github.com/actualbudget/actual/pull/4253
|
||||
'@typescript-eslint/no-unused-vars': 'off',
|
||||
},
|
||||
},
|
||||
];
|
||||
|
||||
@@ -19,6 +19,9 @@
|
||||
},
|
||||
"scripts": {
|
||||
"start": "yarn start:browser",
|
||||
"start:server": "yarn workspace @actual-app/sync-server start",
|
||||
"start:server-monitor": "yarn workspace @actual-app/sync-server start-monitor",
|
||||
"start:server-dev": "NODE_ENV=development BROWSER_OPEN=localhost:5006 yarn npm-run-all --parallel 'start:server-monitor' 'start'",
|
||||
"start:desktop": "yarn rebuild-electron && npm-run-all --parallel 'start:desktop-*'",
|
||||
"start:desktop-node": "yarn workspace loot-core watch:node",
|
||||
"start:desktop-client": "yarn workspace @actual-app/web watch",
|
||||
@@ -40,6 +43,7 @@
|
||||
"rebuild-node": "yarn workspace loot-core rebuild",
|
||||
"lint": "eslint . --max-warnings 0",
|
||||
"lint:verbose": "DEBUG=eslint:cli-engine eslint . --max-warnings 0",
|
||||
"install:server": "yarn workspaces focus @actual-app/sync-server --production",
|
||||
"typecheck": "yarn tsc && tsc-strict",
|
||||
"jq": "./node_modules/node-jq/bin/jq",
|
||||
"prepare": "husky"
|
||||
|
||||
@@ -1,8 +1,7 @@
|
||||
import type {
|
||||
RequestInfo as FetchInfo,
|
||||
RequestInit as FetchInit,
|
||||
// @ts-ignore: false-positive commonjs module error on build until typescript 5.3
|
||||
} from 'node-fetch'; // with { 'resolution-mode': 'import' };
|
||||
} from 'node-fetch';
|
||||
|
||||
// loot-core types
|
||||
import type { InitConfig } from 'loot-core/server/main';
|
||||
@@ -16,9 +15,6 @@ import { validateNodeVersion } from './validateNodeVersion';
|
||||
let actualApp: null | typeof bundle.lib;
|
||||
export const internal = bundle.lib;
|
||||
|
||||
// DEPRECATED: remove the next line in @actual-app/api v7
|
||||
export * as methods from './methods';
|
||||
|
||||
export * from './methods';
|
||||
export * as utils from './utils';
|
||||
|
||||
|
||||
@@ -1,5 +1,5 @@
|
||||
// @ts-strict-ignore
|
||||
import type { Handlers } from 'loot-core/src/types/handlers';
|
||||
import type { Handlers } from 'loot-core/types/handlers';
|
||||
|
||||
import * as injected from './injected';
|
||||
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
{
|
||||
"name": "@actual-app/api",
|
||||
"version": "25.1.0",
|
||||
"version": "25.3.1",
|
||||
"license": "MIT",
|
||||
"description": "An API for Actual",
|
||||
"engines": {
|
||||
|
||||
@@ -11,7 +11,6 @@
|
||||
"outDir": "dist",
|
||||
"declarationDir": "@types",
|
||||
"paths": {
|
||||
"loot-core/src/*": ["./loot-core/*"],
|
||||
"loot-core/*": ["./@types/loot-core/*"]
|
||||
}
|
||||
},
|
||||
|
||||
40
packages/component-library/package.json
Normal file
@@ -0,0 +1,40 @@
|
||||
{
|
||||
"name": "@actual-app/components",
|
||||
"version": "0.0.1",
|
||||
"license": "MIT",
|
||||
"peerDependencies": {
|
||||
"react": ">=18.2"
|
||||
},
|
||||
"dependencies": {
|
||||
"@emotion/css": "^11.13.4",
|
||||
"react-aria-components": "^1.4.1"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@types/react": "^18.2.0",
|
||||
"react": "18.2.0"
|
||||
},
|
||||
"exports": {
|
||||
"./icons/*": "./src/icons/*.tsx",
|
||||
"./aligned-text": "./src/AlignedText.tsx",
|
||||
"./block": "./src/Block.tsx",
|
||||
"./button": "./src/Button.tsx",
|
||||
"./card": "./src/Card.tsx",
|
||||
"./form-error": "./src/FormError.tsx",
|
||||
"./initial-focus": "./src/InitialFocus.ts",
|
||||
"./inline-field": "./src/InlineField.tsx",
|
||||
"./label": "./src/Label.tsx",
|
||||
"./menu": "./src/Menu.tsx",
|
||||
"./paragraph": "./src/Paragraph.tsx",
|
||||
"./popover": "./src/Popover.tsx",
|
||||
"./space-between": "./src/SpaceBetween.tsx",
|
||||
"./stack": "./src/Stack.tsx",
|
||||
"./styles": "./src/styles.ts",
|
||||
"./text": "./src/Text.tsx",
|
||||
"./text-one-line": "./src/TextOneLine.tsx",
|
||||
"./theme": "./src/theme.ts",
|
||||
"./tokens": "./src/tokens.ts",
|
||||
"./toggle": "./src/Toggle.tsx",
|
||||
"./tooltip": "./src/Tooltip.tsx",
|
||||
"./view": "./src/View.tsx"
|
||||
}
|
||||
}
|
||||
@@ -2,7 +2,7 @@ import { type HTMLProps, type Ref } from 'react';
|
||||
|
||||
import { css, cx } from '@emotion/css';
|
||||
|
||||
import { type CSSProperties } from '../../style';
|
||||
import { type CSSProperties } from './styles';
|
||||
|
||||
type BlockProps = HTMLProps<HTMLDivElement> & {
|
||||
innerRef?: Ref<HTMLDivElement>;
|
||||
@@ -9,9 +9,9 @@ import { Button as ReactAriaButton } from 'react-aria-components';
|
||||
|
||||
import { css } from '@emotion/css';
|
||||
|
||||
import { AnimatedLoading } from '../../icons/AnimatedLoading';
|
||||
import { styles, theme } from '../../style';
|
||||
|
||||
import { AnimatedLoading } from './icons/AnimatedLoading';
|
||||
import { styles } from './styles';
|
||||
import { theme } from './theme';
|
||||
import { View } from './View';
|
||||
|
||||
const backgroundColor: {
|
||||
@@ -1,7 +1,6 @@
|
||||
import { type ComponentProps, forwardRef } from 'react';
|
||||
|
||||
import { theme } from '../../style';
|
||||
|
||||
import { theme } from './theme';
|
||||
import { View } from './View';
|
||||
|
||||
type CardProps = ComponentProps<typeof View>;
|
||||
@@ -2,7 +2,7 @@ import { type ReactNode } from 'react';
|
||||
|
||||
import { css } from '@emotion/css';
|
||||
|
||||
import { type CSSProperties } from '../../style';
|
||||
import { type CSSProperties } from './styles';
|
||||
|
||||
type InlineFieldProps = {
|
||||
label: ReactNode;
|
||||
@@ -1,8 +1,8 @@
|
||||
import { forwardRef, type ReactNode, type CSSProperties } from 'react';
|
||||
|
||||
import { theme, styles } from '../../style';
|
||||
|
||||
import { styles } from './styles';
|
||||
import { Text } from './Text';
|
||||
import { theme } from './theme';
|
||||
|
||||
type LabelProps = {
|
||||
title: ReactNode;
|
||||
@@ -8,9 +8,8 @@ import {
|
||||
type CSSProperties,
|
||||
} from 'react';
|
||||
|
||||
import { theme } from '../../style';
|
||||
|
||||
import { Text } from './Text';
|
||||
import { theme } from './theme';
|
||||
import { Toggle } from './Toggle';
|
||||
import { View } from './View';
|
||||
|
||||
@@ -2,7 +2,7 @@ import { type HTMLProps } from 'react';
|
||||
|
||||
import { css } from '@emotion/css';
|
||||
|
||||
import { type CSSProperties } from '../../style';
|
||||
import { type CSSProperties } from './styles';
|
||||
|
||||
type ParagraphProps = HTMLProps<HTMLDivElement> & {
|
||||
style?: CSSProperties;
|
||||
@@ -3,7 +3,7 @@ import { Popover as ReactAriaPopover } from 'react-aria-components';
|
||||
|
||||
import { css } from '@emotion/css';
|
||||
|
||||
import { styles } from '../../style';
|
||||
import { styles } from './styles';
|
||||
|
||||
type PopoverProps = ComponentProps<typeof ReactAriaPopover>;
|
||||
|
||||
@@ -7,7 +7,7 @@ import React, {
|
||||
|
||||
import { css, cx } from '@emotion/css';
|
||||
|
||||
import { type CSSProperties } from '../../style';
|
||||
import { type CSSProperties } from './styles';
|
||||
|
||||
type TextProps = HTMLProps<HTMLSpanElement> & {
|
||||
innerRef?: Ref<HTMLSpanElement>;
|
||||
@@ -2,8 +2,7 @@ import React, { type CSSProperties } from 'react';
|
||||
|
||||
import { css } from '@emotion/css';
|
||||
|
||||
import { theme } from '../../style';
|
||||
|
||||
import { theme } from './theme';
|
||||
import { View } from './View';
|
||||
|
||||
type ToggleProps = {
|
||||
@@ -8,8 +8,7 @@ import React, {
|
||||
} from 'react';
|
||||
import { Tooltip as AriaTooltip, TooltipTrigger } from 'react-aria-components';
|
||||
|
||||
import { styles } from '../../style';
|
||||
|
||||
import { styles } from './styles';
|
||||
import { View } from './View';
|
||||
|
||||
type TooltipProps = Partial<ComponentProps<typeof AriaTooltip>> & {
|
||||
@@ -2,7 +2,7 @@ import React, { forwardRef, type HTMLProps, type Ref } from 'react';
|
||||
|
||||
import { css, cx } from '@emotion/css';
|
||||
|
||||
import { type CSSProperties } from '../../style';
|
||||
import { type CSSProperties } from './styles';
|
||||
|
||||
type ViewProps = HTMLProps<HTMLDivElement> & {
|
||||
className?: string;
|
||||
26
packages/component-library/src/icons/AnimatedLoading.tsx
Normal file
@@ -0,0 +1,26 @@
|
||||
import React, { type SVGProps } from 'react';
|
||||
|
||||
import { css, keyframes } from '@emotion/css';
|
||||
|
||||
import { SvgLoading } from './Loading';
|
||||
|
||||
const rotation = keyframes({
|
||||
'0%': { transform: 'rotate(-90deg)' },
|
||||
'100%': { transform: 'rotate(666deg)' },
|
||||
});
|
||||
|
||||
export function AnimatedLoading(props: SVGProps<SVGSVGElement>) {
|
||||
return (
|
||||
<span
|
||||
className={css({
|
||||
animationName: rotation,
|
||||
animationDuration: '1.6s',
|
||||
animationTimingFunction: 'cubic-bezier(0.17, 0.67, 0.83, 0.67)',
|
||||
animationIterationCount: 'infinite',
|
||||
lineHeight: 0,
|
||||
})}
|
||||
>
|
||||
<SvgLoading {...props} />
|
||||
</span>
|
||||
);
|
||||
}
|
||||
33
packages/component-library/src/icons/Loading.tsx
Normal file
@@ -0,0 +1,33 @@
|
||||
import React, { type SVGProps, useState } from 'react';
|
||||
|
||||
export const SvgLoading = (props: SVGProps<SVGSVGElement>) => {
|
||||
const { color = 'currentColor' } = props;
|
||||
const [gradientId] = useState('gradient-' + Math.random());
|
||||
|
||||
return (
|
||||
<svg {...props} viewBox="0 0 38 38" style={{ ...props.style }}>
|
||||
<defs>
|
||||
<linearGradient
|
||||
x1="8.042%"
|
||||
y1="0%"
|
||||
x2="65.682%"
|
||||
y2="23.865%"
|
||||
id={gradientId}
|
||||
>
|
||||
<stop stopColor={color} stopOpacity={0} offset="0%" />
|
||||
<stop stopColor={color} stopOpacity={0.631} offset="63.146%" />
|
||||
<stop stopColor={color} offset="100%" />
|
||||
</linearGradient>
|
||||
</defs>
|
||||
<g transform="translate(1 2)" fill="none" fillRule="evenodd">
|
||||
<path
|
||||
d="M36 18c0-9.94-8.06-18-18-18"
|
||||
stroke={'url(#' + gradientId + ')'}
|
||||
strokeWidth={2}
|
||||
fill="none"
|
||||
/>
|
||||
<circle fill={color} cx={36} cy={18} r={1} />
|
||||
</g>
|
||||
</svg>
|
||||
);
|
||||
};
|
||||
157
packages/component-library/src/styles.ts
Normal file
@@ -0,0 +1,157 @@
|
||||
import { keyframes } from '@emotion/css';
|
||||
|
||||
import { theme } from './theme';
|
||||
import { tokens } from './tokens';
|
||||
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
export type CSSProperties = Record<string, any>;
|
||||
|
||||
const MOBILE_MIN_HEIGHT = 40;
|
||||
|
||||
const shadowLarge = {
|
||||
boxShadow: '0 15px 30px 0 rgba(0,0,0,0.11), 0 5px 15px 0 rgba(0,0,0,0.08)',
|
||||
};
|
||||
|
||||
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
||||
export const styles: Record<string, any> = {
|
||||
incomeHeaderHeight: 70,
|
||||
cardShadow: '0 1px 3px rgba(0,0,0,0.12), 0 1px 2px rgba(0,0,0,0.24)',
|
||||
monthRightPadding: 5,
|
||||
menuBorderRadius: 4,
|
||||
mobileMinHeight: MOBILE_MIN_HEIGHT,
|
||||
mobileMenuItem: {
|
||||
fontSize: 17,
|
||||
fontWeight: 400,
|
||||
paddingTop: 8,
|
||||
paddingBottom: 8,
|
||||
height: MOBILE_MIN_HEIGHT,
|
||||
minHeight: MOBILE_MIN_HEIGHT,
|
||||
},
|
||||
mobileEditingPadding: 12,
|
||||
altMenuMaxHeight: 250,
|
||||
altMenuText: {
|
||||
fontSize: 13,
|
||||
},
|
||||
altMenuHeaderText: {
|
||||
fontSize: 13,
|
||||
fontWeight: 700,
|
||||
},
|
||||
veryLargeText: {
|
||||
fontSize: 30,
|
||||
fontWeight: 600,
|
||||
},
|
||||
largeText: {
|
||||
fontSize: 20,
|
||||
fontWeight: 700,
|
||||
letterSpacing: 0.5,
|
||||
},
|
||||
mediumText: {
|
||||
fontSize: 15,
|
||||
fontWeight: 500,
|
||||
},
|
||||
smallText: {
|
||||
fontSize: 13,
|
||||
},
|
||||
verySmallText: {
|
||||
fontSize: 12,
|
||||
},
|
||||
tinyText: {
|
||||
fontSize: 10,
|
||||
},
|
||||
page: {
|
||||
flex: 1,
|
||||
'@media (max-height: 550px)': {
|
||||
minHeight: 700, // ensure we can scroll on small screens
|
||||
},
|
||||
paddingTop: 8, // height of the titlebar
|
||||
[`@media (min-width: ${tokens.breakpoint_small})`]: {
|
||||
paddingTop: 36,
|
||||
},
|
||||
},
|
||||
pageContent: {
|
||||
paddingLeft: 2,
|
||||
paddingRight: 2,
|
||||
[`@media (min-width: ${tokens.breakpoint_small})`]: {
|
||||
paddingLeft: 20,
|
||||
paddingRight: 20,
|
||||
},
|
||||
},
|
||||
settingsPageContent: {
|
||||
padding: 20,
|
||||
[`@media (min-width: ${tokens.breakpoint_small})`]: {
|
||||
padding: 'inherit',
|
||||
},
|
||||
},
|
||||
staticText: {
|
||||
cursor: 'default',
|
||||
userSelect: 'none',
|
||||
},
|
||||
shadow: {
|
||||
boxShadow: '0 2px 4px 0 rgba(0,0,0,0.1)',
|
||||
},
|
||||
shadowLarge,
|
||||
tnum: {
|
||||
// eslint-disable-next-line rulesdir/typography
|
||||
fontFeatureSettings: '"tnum"',
|
||||
},
|
||||
notFixed: { fontFeatureSettings: '' },
|
||||
text: {
|
||||
fontSize: 16,
|
||||
// lineHeight: 22.4 // TODO: This seems like trouble, but what's the right value?
|
||||
},
|
||||
delayedFadeIn: {
|
||||
animationName: keyframes({
|
||||
'0%': { opacity: 0 },
|
||||
'100%': { opacity: 1 },
|
||||
}),
|
||||
animationDuration: '1s',
|
||||
animationFillMode: 'both',
|
||||
animationDelay: '0.5s',
|
||||
},
|
||||
underlinedText: {
|
||||
borderBottom: `2px solid`,
|
||||
},
|
||||
noTapHighlight: {
|
||||
WebkitTapHighlightColor: 'transparent',
|
||||
':focus': {
|
||||
outline: 'none',
|
||||
},
|
||||
},
|
||||
lineClamp: (lines: number) => {
|
||||
return {
|
||||
display: '-webkit-box',
|
||||
WebkitLineClamp: lines,
|
||||
WebkitBoxOrient: 'vertical',
|
||||
overflow: 'hidden',
|
||||
textOverflow: 'ellipsis',
|
||||
wordBreak: 'break-word',
|
||||
};
|
||||
},
|
||||
tooltip: {
|
||||
padding: 5,
|
||||
...shadowLarge,
|
||||
borderWidth: 2,
|
||||
borderRadius: 4,
|
||||
borderStyle: 'solid',
|
||||
borderColor: theme.tooltipBorder,
|
||||
backgroundColor: theme.tooltipBackground,
|
||||
color: theme.tooltipText,
|
||||
overflow: 'auto',
|
||||
},
|
||||
popover: {
|
||||
border: 'none',
|
||||
backgroundColor: theme.menuBackground,
|
||||
color: theme.menuItemText,
|
||||
},
|
||||
// Dynamically set
|
||||
horizontalScrollbar: null as CSSProperties | null,
|
||||
lightScrollbar: null as CSSProperties | null,
|
||||
darkScrollbar: null as CSSProperties | null,
|
||||
scrollbarWidth: null as number | null,
|
||||
editorPill: {
|
||||
color: theme.pillText,
|
||||
backgroundColor: theme.pillBackground,
|
||||
borderRadius: 4,
|
||||
padding: '3px 5px',
|
||||
},
|
||||
};
|
||||
203
packages/component-library/src/theme.ts
Normal file
@@ -0,0 +1,203 @@
|
||||
export const theme = {
|
||||
pageBackground: 'var(--color-pageBackground)',
|
||||
pageBackgroundModalActive: 'var(--color-pageBackgroundModalActive)',
|
||||
pageBackgroundTopLeft: 'var(--color-pageBackgroundTopLeft)',
|
||||
pageBackgroundBottomRight: 'var(--color-pageBackgroundBottomRight)',
|
||||
pageBackgroundLineTop: 'var(--color-pageBackgroundLineTop)',
|
||||
pageBackgroundLineMid: 'var(--color-pageBackgroundLineMid)',
|
||||
pageBackgroundLineBottom: 'var(--color-pageBackgroundLineBottom)',
|
||||
pageText: 'var(--color-pageText)',
|
||||
pageTextLight: 'var(--color-pageTextLight)',
|
||||
pageTextSubdued: 'var(--color-pageTextSubdued)',
|
||||
pageTextDark: 'var(--color-pageTextDark)',
|
||||
pageTextPositive: 'var(--color-pageTextPositive)',
|
||||
pageTextLink: 'var(--color-pageTextLink)',
|
||||
pageTextLinkLight: 'var(--color-pageTextLinkLight)',
|
||||
cardBackground: 'var(--color-cardBackground)',
|
||||
cardBorder: 'var(--color-cardBorder)',
|
||||
cardShadow: 'var(--color-cardShadow)',
|
||||
tableBackground: 'var(--color-tableBackground)',
|
||||
tableRowBackgroundHover: 'var(--color-tableRowBackgroundHover)',
|
||||
tableText: 'var(--color-tableText)',
|
||||
tableTextLight: 'var(--color-tableTextLight)',
|
||||
tableTextSubdued: 'var(--color-tableTextSubdued)',
|
||||
tableTextSelected: 'var(--color-tableTextSelected)',
|
||||
tableTextHover: 'var(--color-tableTextHover)',
|
||||
tableTextInactive: 'var(--color-tableTextInactive)',
|
||||
tableHeaderText: 'var(--color-tableHeaderText)',
|
||||
tableHeaderBackground: 'var(--color-tableHeaderBackground)',
|
||||
tableBorder: 'var(--color-tableBorder)',
|
||||
tableBorderSelected: 'var(--color-tableBorderSelected)',
|
||||
tableBorderHover: 'var(--color-tableBorderHover)',
|
||||
tableBorderSeparator: 'var(--color-tableBorderSeparator)',
|
||||
tableRowBackgroundHighlight: 'var(--color-tableRowBackgroundHighlight)',
|
||||
tableRowBackgroundHighlightText:
|
||||
'var(--color-tableRowBackgroundHighlightText)',
|
||||
tableRowHeaderBackground: 'var(--color-tableRowHeaderBackground)',
|
||||
tableRowHeaderText: 'var(--color-tableRowHeaderText)',
|
||||
sidebarBackground: 'var(--color-sidebarBackground)',
|
||||
sidebarItemBackgroundPending: 'var(--color-sidebarItemBackgroundPending)',
|
||||
sidebarItemBackgroundPositive: 'var(--color-sidebarItemBackgroundPositive)',
|
||||
sidebarItemBackgroundFailed: 'var(--color-sidebarItemBackgroundFailed)',
|
||||
sidebarItemAccentSelected: 'var(--color-sidebarItemAccentSelected)',
|
||||
sidebarItemBackgroundHover: 'var(--color-sidebarItemBackgroundHover)',
|
||||
sidebarItemText: 'var(--color-sidebarItemText)',
|
||||
sidebarItemTextSelected: 'var(--color-sidebarItemTextSelected)',
|
||||
menuBackground: 'var(--color-menuBackground)',
|
||||
menuItemBackground: 'var(--color-menuItemBackground)',
|
||||
menuItemBackgroundHover: 'var(--color-menuItemBackgroundHover)',
|
||||
menuItemText: 'var(--color-menuItemText)',
|
||||
menuItemTextHover: 'var(--color-menuItemTextHover)',
|
||||
menuItemTextSelected: 'var(--color-menuItemTextSelected)',
|
||||
menuItemTextHeader: 'var(--color-menuItemTextHeader)',
|
||||
menuBorder: 'var(--color-menuBorder)',
|
||||
menuBorderHover: 'var(--color-menuBorderHover)',
|
||||
menuKeybindingText: 'var(--color-menuKeybindingText)',
|
||||
menuAutoCompleteBackground: 'var(--color-menuAutoCompleteBackground)',
|
||||
menuAutoCompleteBackgroundHover:
|
||||
'var(--color-menuAutoCompleteBackgroundHover)',
|
||||
menuAutoCompleteText: 'var(--color-menuAutoCompleteText)',
|
||||
menuAutoCompleteTextHover: 'var(--color-menuAutoCompleteTextHover)',
|
||||
menuAutoCompleteTextHeader: 'var(--color-menuAutoCompleteTextHeader)',
|
||||
menuAutoCompleteItemTextHover: 'var(--color-menuAutoCompleteItemTextHover)',
|
||||
menuAutoCompleteItemText: 'var(--color-menuAutoCompleteItemText)',
|
||||
modalBackground: 'var(--color-modalBackground)',
|
||||
modalBorder: 'var(--color-modalBorder)',
|
||||
mobileHeaderBackground: 'var(--color-mobileHeaderBackground)',
|
||||
mobileHeaderText: 'var(--color-mobileHeaderText)',
|
||||
mobileHeaderTextSubdued: 'var(--color-mobileHeaderTextSubdued)',
|
||||
mobileHeaderTextHover: 'var(--color-mobileHeaderTextHover)',
|
||||
mobilePageBackground: 'var(--color-mobilePageBackground)',
|
||||
mobileNavBackground: 'var(--color-mobileNavBackground)',
|
||||
mobileNavItem: 'var(--color-mobileNavItem)',
|
||||
mobileNavItemSelected: 'var(--color-mobileNavItemSelected)',
|
||||
mobileAccountShadow: 'var(--color-mobileAccountShadow)',
|
||||
mobileAccountText: 'var(--color-mobileAccountText)',
|
||||
mobileTransactionSelected: 'var(--color-mobileTransactionSelected)',
|
||||
mobileViewTheme: 'var(--color-mobileViewTheme)',
|
||||
mobileConfigServerViewTheme: 'var(--color-mobileConfigServerViewTheme)',
|
||||
markdownNormal: 'var(--color-markdownNormal)',
|
||||
markdownDark: 'var(--color-markdownDark)',
|
||||
markdownLight: 'var(--color-markdownLight)',
|
||||
buttonMenuText: 'var(--color-buttonMenuText)',
|
||||
buttonMenuTextHover: 'var(--color-buttonMenuTextHover)',
|
||||
buttonMenuBackground: 'var(--color-buttonMenuBackground)',
|
||||
buttonMenuBackgroundHover: 'var(--color-buttonMenuBackgroundHover)',
|
||||
buttonMenuBorder: 'var(--color-buttonMenuBorder)',
|
||||
buttonMenuSelectedText: 'var(--color-buttonMenuSelectedText)',
|
||||
buttonMenuSelectedTextHover: 'var(--color-buttonMenuSelectedTextHover)',
|
||||
buttonMenuSelectedBackground: 'var(--color-buttonMenuSelectedBackground)',
|
||||
buttonMenuSelectedBackgroundHover:
|
||||
'var(--color-buttonMenuSelectedBackgroundHover)',
|
||||
buttonMenuSelectedBorder: 'var(--color-buttonMenuSelectedBorder)',
|
||||
buttonPrimaryText: 'var(--color-buttonPrimaryText)',
|
||||
buttonPrimaryTextHover: 'var(--color-buttonPrimaryTextHover)',
|
||||
buttonPrimaryBackground: 'var(--color-buttonPrimaryBackground)',
|
||||
buttonPrimaryBackgroundHover: 'var(--color-buttonPrimaryBackgroundHover)',
|
||||
buttonPrimaryBorder: 'var(--color-buttonPrimaryBorder)',
|
||||
buttonPrimaryShadow: 'var(--color-buttonPrimaryShadow)',
|
||||
buttonPrimaryDisabledText: 'var(--color-buttonPrimaryDisabledText)',
|
||||
buttonPrimaryDisabledBackground:
|
||||
'var(--color-buttonPrimaryDisabledBackground)',
|
||||
buttonPrimaryDisabledBorder: 'var(--color-buttonPrimaryDisabledBorder)',
|
||||
buttonNormalText: 'var(--color-buttonNormalText)',
|
||||
buttonNormalTextHover: 'var(--color-buttonNormalTextHover)',
|
||||
buttonNormalBackground: 'var(--color-buttonNormalBackground)',
|
||||
buttonNormalBackgroundHover: 'var(--color-buttonNormalBackgroundHover)',
|
||||
buttonNormalBorder: 'var(--color-buttonNormalBorder)',
|
||||
buttonNormalShadow: 'var(--color-buttonNormalShadow)',
|
||||
buttonNormalSelectedText: 'var(--color-buttonNormalSelectedText)',
|
||||
buttonNormalSelectedBackground: 'var(--color-buttonNormalSelectedBackground)',
|
||||
buttonNormalDisabledText: 'var(--color-buttonNormalDisabledText)',
|
||||
buttonNormalDisabledBackground: 'var(--color-buttonNormalDisabledBackground)',
|
||||
buttonNormalDisabledBorder: 'var(--color-buttonNormalDisabledBorder)',
|
||||
buttonBareText: 'var(--color-buttonBareText)',
|
||||
buttonBareTextHover: 'var(--color-buttonBareTextHover)',
|
||||
buttonBareBackground: 'var(--color-buttonBareBackground)',
|
||||
buttonBareBackgroundHover: 'var(--color-buttonBareBackgroundHover)',
|
||||
buttonBareBackgroundActive: 'var(--color-buttonBareBackgroundActive)',
|
||||
buttonBareDisabledText: 'var(--color-buttonBareDisabledText)',
|
||||
buttonBareDisabledBackground: 'var(--color-buttonBareDisabledBackground)',
|
||||
calendarText: 'var(--color-calendarText)',
|
||||
calendarBackground: 'var(--color-calendarBackground)',
|
||||
calendarItemText: 'var(--color-calendarItemText)',
|
||||
calendarItemBackground: 'var(--color-calendarItemBackground)',
|
||||
calendarSelectedBackground: 'var(--color-calendarSelectedBackground)',
|
||||
noticeBackground: 'var(--color-noticeBackground)',
|
||||
noticeBackgroundLight: 'var(--color-noticeBackgroundLight)',
|
||||
noticeBackgroundDark: 'var(--color-noticeBackgroundDark)',
|
||||
noticeText: 'var(--color-noticeText)',
|
||||
noticeTextLight: 'var(--color-noticeTextLight)',
|
||||
noticeTextDark: 'var(--color-noticeTextDark)',
|
||||
noticeTextMenu: 'var(--color-noticeTextMenu)',
|
||||
noticeTextMenuHover: 'var(--color-noticeTextMenuHover)',
|
||||
noticeBorder: 'var(--color-noticeBorder)',
|
||||
warningBackground: 'var(--color-warningBackground)',
|
||||
warningText: 'var(--color-warningText)',
|
||||
warningTextLight: 'var(--color-warningTextLight)',
|
||||
warningTextDark: 'var(--color-warningTextDark)',
|
||||
warningBorder: 'var(--color-warningBorder)',
|
||||
errorBackground: 'var(--color-errorBackground)',
|
||||
errorText: 'var(--color-errorText)',
|
||||
errorTextDark: 'var(--color-errorTextDark)',
|
||||
errorTextDarker: 'var(--color-errorTextDarker)',
|
||||
errorTextMenu: 'var(--color-errorTextMenu)',
|
||||
errorBorder: 'var(--color-errorBorder)',
|
||||
upcomingBackground: 'var(--color-upcomingBackground)',
|
||||
upcomingText: 'var(--color-upcomingText)',
|
||||
upcomingBorder: 'var(--color-upcomingBorder)',
|
||||
formLabelText: 'var(--color-formLabelText)',
|
||||
formLabelBackground: 'var(--color-formLabelBackground)',
|
||||
formInputBackground: 'var(--color-formInputBackground)',
|
||||
formInputBackgroundSelected: 'var(--color-formInputBackgroundSelected)',
|
||||
formInputBackgroundSelection: 'var(--color-formInputBackgroundSelection)',
|
||||
formInputBorder: 'var(--color-formInputBorder)',
|
||||
formInputTextReadOnlySelection: 'var(--color-formInputTextReadOnlySelection)',
|
||||
formInputBorderSelected: 'var(--color-formInputBorderSelected)',
|
||||
formInputText: 'var(--color-formInputText)',
|
||||
formInputTextSelected: 'var(--color-formInputTextSelected)',
|
||||
formInputTextPlaceholder: 'var(--color-formInputTextPlaceholder)',
|
||||
formInputTextPlaceholderSelected:
|
||||
'var(--color-formInputTextPlaceholderSelected)',
|
||||
formInputTextSelection: 'var(--color-formInputTextSelection)',
|
||||
formInputShadowSelected: 'var(--color-formInputShadowSelected)',
|
||||
formInputTextHighlight: 'var(--color-formInputTextHighlight)',
|
||||
checkboxText: 'var(--color-checkboxText)',
|
||||
checkboxBackgroundSelected: 'var(--color-checkboxBackgroundSelected)',
|
||||
checkboxBorderSelected: 'var(--color-checkboxBorderSelected)',
|
||||
checkboxShadowSelected: 'var(--color-checkboxShadowSelected)',
|
||||
checkboxToggleBackground: 'var(--color-checkboxToggleBackground)',
|
||||
checkboxToggleBackgroundSelected:
|
||||
'var(--color-checkboxToggleBackgroundSelected)',
|
||||
checkboxToggleDisabled: 'var(--color-checkboxToggleDisabled)',
|
||||
pillBackground: 'var(--color-pillBackground)',
|
||||
pillBackgroundLight: 'var(--color-pillBackgroundLight)',
|
||||
pillText: 'var(--color-pillText)',
|
||||
pillTextHighlighted: 'var(--color-pillTextHighlighted)',
|
||||
pillBorder: 'var(--color-pillBorder)',
|
||||
pillBorderDark: 'var(--color-pillBorderDark)',
|
||||
pillBackgroundSelected: 'var(--color-pillBackgroundSelected)',
|
||||
pillTextSelected: 'var(--color-pillTextSelected)',
|
||||
pillBorderSelected: 'var(--color-pillBorderSelected)',
|
||||
pillTextSubdued: 'var(--color-pillTextSubdued)',
|
||||
reportsRed: 'var(--color-reportsRed)',
|
||||
reportsBlue: 'var(--color-reportsBlue)',
|
||||
reportsGreen: 'var(--color-reportsGreen)',
|
||||
reportsGray: 'var(--color-reportsGray)',
|
||||
reportsLabel: 'var(--color-reportsLabel)',
|
||||
reportsInnerLabel: 'var(--color-reportsInnerLabel)',
|
||||
noteTagBackground: 'var(--color-noteTagBackground)',
|
||||
noteTagBackgroundHover: 'var(--color-noteTagBackgroundHover)',
|
||||
noteTagText: 'var(--color-noteTagText)',
|
||||
budgetOtherMonth: 'var(--color-budgetOtherMonth)',
|
||||
budgetCurrentMonth: 'var(--color-budgetCurrentMonth)',
|
||||
budgetHeaderOtherMonth: 'var(--color-budgetHeaderOtherMonth)',
|
||||
budgetHeaderCurrentMonth: 'var(--color-budgetHeaderCurrentMonth)',
|
||||
floatingActionBarBackground: 'var(--color-floatingActionBarBackground)',
|
||||
floatingActionBarBorder: 'var(--color-floatingActionBarBorder)',
|
||||
floatingActionBarText: 'var(--color-floatingActionBarText)',
|
||||
tooltipText: 'var(--color-tooltipText)',
|
||||
tooltipBackground: 'var(--color-tooltipBackground)',
|
||||
tooltipBorder: 'var(--color-tooltipBorder)',
|
||||
calendarCellBackground: 'var(--color-calendarCellBackground)',
|
||||
};
|
||||
35
packages/component-library/src/tokens.ts
Normal file
@@ -0,0 +1,35 @@
|
||||
enum BreakpointNames {
|
||||
small = 'small',
|
||||
medium = 'medium',
|
||||
wide = 'wide',
|
||||
}
|
||||
|
||||
type NumericBreakpoints = {
|
||||
[key in BreakpointNames]: number;
|
||||
};
|
||||
|
||||
export const breakpoints: NumericBreakpoints = {
|
||||
small: 512,
|
||||
medium: 730,
|
||||
wide: 1100,
|
||||
};
|
||||
|
||||
type BreakpointsPx = {
|
||||
[B in keyof NumericBreakpoints as `breakpoint_${B}`]: string;
|
||||
};
|
||||
|
||||
// Provide the same breakpoints in a form usable by CSS media queries
|
||||
// {
|
||||
// breakpoint_small: '512px',
|
||||
// breakpoint_medium: '740px',
|
||||
// breakpoint_wide: '1100px',
|
||||
// }
|
||||
export const tokens: BreakpointsPx = Object.entries(
|
||||
breakpoints,
|
||||
).reduce<BreakpointsPx>(
|
||||
(acc, [key, val]) => ({
|
||||
...acc,
|
||||
[`breakpoint_${key}`]: `${val}px`,
|
||||
}),
|
||||
{} as BreakpointsPx,
|
||||
);
|
||||
@@ -23,6 +23,11 @@ const processTranslations = () => {
|
||||
files.forEach((file) => {
|
||||
if (file === 'en.json' || path.extname(file) !== '.json') return;
|
||||
|
||||
if (file.startsWith('en-')) {
|
||||
console.log(`Keeping ${file} as it's an English language.`);
|
||||
return;
|
||||
}
|
||||
|
||||
const filePath = path.join(localRepoPath, file);
|
||||
const jsonData = JSON.parse(fs.readFileSync(filePath, 'utf8'));
|
||||
const fileKeysCount = Object.keys(jsonData).length;
|
||||
|
||||
|
Before Width: | Height: | Size: 32 KiB After Width: | Height: | Size: 32 KiB |
|
Before Width: | Height: | Size: 33 KiB After Width: | Height: | Size: 33 KiB |
|
Before Width: | Height: | Size: 33 KiB After Width: | Height: | Size: 33 KiB |
|
Before Width: | Height: | Size: 116 KiB After Width: | Height: | Size: 116 KiB |
|
Before Width: | Height: | Size: 116 KiB After Width: | Height: | Size: 116 KiB |
|
Before Width: | Height: | Size: 117 KiB After Width: | Height: | Size: 117 KiB |
|
Before Width: | Height: | Size: 56 KiB After Width: | Height: | Size: 56 KiB |
|
Before Width: | Height: | Size: 56 KiB After Width: | Height: | Size: 56 KiB |
|
Before Width: | Height: | Size: 56 KiB After Width: | Height: | Size: 56 KiB |
@@ -1,7 +1,7 @@
|
||||
import { type Page } from '@playwright/test';
|
||||
|
||||
import * as monthUtils from 'loot-core/shared/months';
|
||||
import { amountToCurrency, currencyToAmount } from 'loot-core/shared/util';
|
||||
import * as monthUtils from 'loot-core/src/shared/months';
|
||||
|
||||
import { expect, test } from './fixtures';
|
||||
import { ConfigurationPage } from './page-models/configuration-page';
|
||||
@@ -60,6 +60,9 @@ async function setBudgetAverage(
|
||||
await budgetPage.goToPreviousMonth();
|
||||
const spentButton = await budgetPage.getButtonForSpent(categoryName);
|
||||
const spent = await spentButton.textContent();
|
||||
if (!spent) {
|
||||
throw new Error('Failed to get spent amount');
|
||||
}
|
||||
totalSpent += currencyToAmount(spent) ?? 0;
|
||||
}
|
||||
|
||||
@@ -280,6 +283,10 @@ budgetTypes.forEach(budgetType => {
|
||||
|
||||
const lastMonthBudget = await budgetedButton.textContent();
|
||||
|
||||
if (!lastMonthBudget) {
|
||||
throw new Error('Failed to get last month budget');
|
||||
}
|
||||
|
||||
await budgetPage.goToNextMonth();
|
||||
|
||||
await copyLastMonthBudget(budgetPage, categoryName);
|
||||
|
||||
|
Before Width: | Height: | Size: 32 KiB After Width: | Height: | Size: 32 KiB |
|
Before Width: | Height: | Size: 32 KiB After Width: | Height: | Size: 32 KiB |
|
Before Width: | Height: | Size: 27 KiB After Width: | Height: | Size: 27 KiB |
|
Before Width: | Height: | Size: 35 KiB After Width: | Height: | Size: 35 KiB |
|
Before Width: | Height: | Size: 32 KiB After Width: | Height: | Size: 31 KiB |
|
Before Width: | Height: | Size: 29 KiB After Width: | Height: | Size: 29 KiB |
|
Before Width: | Height: | Size: 29 KiB After Width: | Height: | Size: 29 KiB |
|
Before Width: | Height: | Size: 32 KiB After Width: | Height: | Size: 32 KiB |
|
Before Width: | Height: | Size: 30 KiB After Width: | Height: | Size: 30 KiB |
|
Before Width: | Height: | Size: 35 KiB After Width: | Height: | Size: 35 KiB |
|
Before Width: | Height: | Size: 31 KiB After Width: | Height: | Size: 31 KiB |
|
Before Width: | Height: | Size: 33 KiB After Width: | Height: | Size: 33 KiB |
|
Before Width: | Height: | Size: 29 KiB After Width: | Height: | Size: 29 KiB |
|
Before Width: | Height: | Size: 27 KiB After Width: | Height: | Size: 27 KiB |
|
Before Width: | Height: | Size: 31 KiB After Width: | Height: | Size: 30 KiB |
|
Before Width: | Height: | Size: 33 KiB After Width: | Height: | Size: 33 KiB |
|
Before Width: | Height: | Size: 31 KiB After Width: | Height: | Size: 31 KiB |
|
Before Width: | Height: | Size: 31 KiB After Width: | Height: | Size: 31 KiB |
|
Before Width: | Height: | Size: 34 KiB After Width: | Height: | Size: 33 KiB |
|
Before Width: | Height: | Size: 33 KiB After Width: | Height: | Size: 33 KiB |
|
Before Width: | Height: | Size: 26 KiB After Width: | Height: | Size: 26 KiB |
|
Before Width: | Height: | Size: 26 KiB After Width: | Height: | Size: 26 KiB |
|
Before Width: | Height: | Size: 30 KiB After Width: | Height: | Size: 30 KiB |
|
Before Width: | Height: | Size: 31 KiB After Width: | Height: | Size: 31 KiB |
|
Before Width: | Height: | Size: 29 KiB After Width: | Height: | Size: 29 KiB |
|
Before Width: | Height: | Size: 30 KiB After Width: | Height: | Size: 30 KiB |
|
Before Width: | Height: | Size: 31 KiB After Width: | Height: | Size: 31 KiB |
|
Before Width: | Height: | Size: 32 KiB After Width: | Height: | Size: 31 KiB |
|
Before Width: | Height: | Size: 32 KiB After Width: | Height: | Size: 32 KiB |
|
Before Width: | Height: | Size: 33 KiB After Width: | Height: | Size: 33 KiB |
|
Before Width: | Height: | Size: 31 KiB After Width: | Height: | Size: 31 KiB |
|
Before Width: | Height: | Size: 32 KiB After Width: | Height: | Size: 32 KiB |
|
Before Width: | Height: | Size: 31 KiB After Width: | Height: | Size: 31 KiB |
|
Before Width: | Height: | Size: 32 KiB After Width: | Height: | Size: 32 KiB |
|
Before Width: | Height: | Size: 32 KiB After Width: | Height: | Size: 32 KiB |
|
Before Width: | Height: | Size: 32 KiB After Width: | Height: | Size: 32 KiB |
|
Before Width: | Height: | Size: 34 KiB After Width: | Height: | Size: 34 KiB |
|
Before Width: | Height: | Size: 27 KiB After Width: | Height: | Size: 27 KiB |
|
Before Width: | Height: | Size: 27 KiB After Width: | Height: | Size: 27 KiB |
|
Before Width: | Height: | Size: 28 KiB After Width: | Height: | Size: 28 KiB |
|
Before Width: | Height: | Size: 27 KiB After Width: | Height: | Size: 28 KiB |
|
Before Width: | Height: | Size: 28 KiB After Width: | Height: | Size: 29 KiB |
|
Before Width: | Height: | Size: 32 KiB After Width: | Height: | Size: 32 KiB |
|
Before Width: | Height: | Size: 32 KiB After Width: | Height: | Size: 33 KiB |
|
Before Width: | Height: | Size: 26 KiB After Width: | Height: | Size: 26 KiB |
|
Before Width: | Height: | Size: 29 KiB After Width: | Height: | Size: 28 KiB |
|
Before Width: | Height: | Size: 25 KiB After Width: | Height: | Size: 25 KiB |
|
Before Width: | Height: | Size: 27 KiB After Width: | Height: | Size: 26 KiB |
|
Before Width: | Height: | Size: 35 KiB After Width: | Height: | Size: 35 KiB |
|
Before Width: | Height: | Size: 29 KiB After Width: | Height: | Size: 29 KiB |
|
Before Width: | Height: | Size: 29 KiB After Width: | Height: | Size: 29 KiB |