Compare commits

...

1050 Commits

Author SHA1 Message Date
lash
c0534ede1b
Strip scheme from connstring in gdbm 2025-01-15 00:32:56 +00:00
lash
24e729d275
Fix untidy go mod 2025-01-15 00:11:11 +00:00
lash
ae6e2a99c5
upgrade vise dep 2025-01-15 00:09:14 +00:00
lash
7ca3974371
Enable fs, mem in storageservice 2025-01-15 00:08:44 +00:00
lash
adbfab3964
Enable conndata fs, mem 2025-01-14 18:57:04 +00:00
lash
5228aef088
Add mem storage service 2025-01-13 21:33:25 +00:00
lash
5bf0a0e858
remove session package 2025-01-13 10:31:42 +00:00
lash
f13dab9a45
Remove docker stuff 2025-01-12 15:54:57 +00:00
lash
3f8e08151a
Add debug string for db type in menuhandler 2025-01-12 15:35:44 +00:00
lash
9e4c65c8b4
Correct storage service interface signature 2025-01-12 12:13:25 +00:00
lash
611c5a8dfc
Rename session handler to request handler 2025-01-12 10:40:23 +00:00
lash
dcf777bf08
Fix missing err in config 2025-01-12 10:24:50 +00:00
lash
ec4ad6e44b
Move out config 2025-01-12 09:37:40 +00:00
lash
5b312f9569
Move out common, util, debug, storage to sarafu-vise 2025-01-12 07:59:03 +00:00
lash
2d89db3a37
Rename http source file 2025-01-11 22:38:38 +00:00
lash
6d8992fe38
Remove remaining devtools cmds 2025-01-11 22:33:03 +00:00
lash
5cffbe5cd8
Remove lang devtool 2025-01-11 22:31:21 +00:00
lash
b28a047777
Remove dialoguss reference 2025-01-11 22:29:08 +00:00
lash
2ea51d88d8
Factor out adminstore 2025-01-11 22:21:09 +00:00
lash
2e0e854c4b
Remove last internal package 2025-01-11 21:47:57 +00:00
lash
c93a07832d
Move out API services related code 2025-01-11 16:31:06 +00:00
lash
46bf21b7b8
Remove commented code 2025-01-11 15:16:14 +00:00
lash
dff662663d
Rehabilitate http server test 2025-01-11 08:37:10 +00:00
lash
977d14c529
Properly isolate http session handler 2025-01-11 08:33:52 +00:00
lash
fd6e5caf53
Remove persister chainer for menu handler 2025-01-11 08:08:52 +00:00
lash
840c22ca89
Factor out session handler, introduce entry handler 2025-01-11 08:01:48 +00:00
lash
f939a20543
Remove vise code 2025-01-11 07:23:15 +00:00
lash
8387644019
Export http package 2025-01-10 20:39:36 +00:00
lash
c535938dbc
Move out remaining local handler dependent code 2025-01-10 20:31:34 +00:00
lash
b60d2648ea
Rehabilitate until localhandler 2025-01-10 14:04:23 +00:00
lash
85ede15613 Merge branch 'master' into lash/purify-max 2025-01-10 13:46:52 +00:00
b11f11b5fa Merge pull request 'refactor: rename files to snake_case' (#268) from konstantinmds/ussd:refactor/148-convert-files-to-snake-case into master
Reviewed-on: urdt/ussd#268
2025-01-10 14:40:58 +01:00
3d35a5de78 rename files to snake case 2025-01-10 13:43:49 +01:00
a19ace85f8 refactor: rename files to snake_case 2025-01-10 13:41:23 +01:00
lash
a7a8a482ab
Rehabilitate go test running 2025-01-10 12:03:37 +00:00
lash
d8e7c443b5
Add gettext in exported storage service 2025-01-10 11:54:59 +00:00
lash
5216a9383e
Add service mock missing 2025-01-10 11:49:47 +00:00
lash
6cd639fd19
Add missing pgxpool module 2025-01-10 11:44:15 +00:00
lash
a7ca280964 Merge branch 'master' into lash/purify-max 2025-01-10 11:40:49 +00:00
8f5ed0cd4f Merge pull request 'postgres-switch-for-tests' (#255) from postgres-switch-for-tests into master
Reviewed-on: urdt/ussd#255
2025-01-10 12:07:07 +01:00
lash
f1664a43a8
Rename module, export storage, testutil 2025-01-10 10:53:27 +00:00
c29abfe21e Merge branch 'master' into postgres-switch-for-tests 2025-01-10 13:43:16 +03:00
9a6d8e5158
Refactored the code to switch between postgres and gdbm, with db cleanup 2025-01-10 13:41:05 +03:00
lash
9ca5091692 Merge branch 'master' into lash/purify-max 2025-01-10 08:56:59 +00:00
db431c750e Merge pull request 'copy-language-code' (#264) from copy-language-code into master
Reviewed-on: urdt/ussd#264
2025-01-10 09:53:17 +01:00
2b9c6d641e
Merge branch 'master' into copy-language-code 2025-01-10 11:06:32 +03:00
lash
b9712098ef
Fix remaining conflict diff 2025-01-09 13:49:50 +00:00
lash
bcf1965a6c Merge branch 'master' into lash/purify-max 2025-01-09 13:48:39 +00:00
3747f87a7c
test language code saving 2025-01-09 15:11:29 +03:00
1f0568df32 Merge pull request 'Implement connstring handling' (#247) from lash/purify-more into master
Reviewed-on: urdt/ussd#247
2025-01-09 13:03:28 +01:00
lash
24c513d4f0 Merge branch 'master' into lash/purify-more 2025-01-09 12:02:17 +00:00
b3fd6f5c1a Merge pull request 'Rename handler/ussd package' (#254) from konstantinmds/ussd:refactor/24-rename-ussd-to-application into master
Reviewed-on: urdt/ussd#254
2025-01-09 13:01:19 +01:00
73eb765408
persist selected language code 2025-01-09 13:14:46 +03:00
f660f6c19a
add key to hold selected langauge code 2025-01-09 13:04:11 +03:00
3fccfaab61
Replace the connStr if it is not set 2025-01-09 13:01:28 +03:00
lash
b50a51df9b
Implement postgres schema 2025-01-09 07:42:09 +00:00
lash
df8c9aab0c
Rehabilitate tests 2025-01-08 22:27:19 +00:00
lash
ddefdd7fb3 Merge branch 'lash/purify-more' into postgres-switch-for-tests 2025-01-08 22:05:12 +00:00
5734011f96 refactor: rename ussd package to application (#24)
- Rename internal/handlers/ussd directory to application
- Update all imports and references to use new package name
2025-01-08 13:40:00 +01:00
lash
379d98ccd5 Merge branch 'master' into lash/purify-more 2025-01-08 12:32:11 +00:00
f40e11c267 Merge pull request 'account-pin-block-v2' (#256) from account-pin-block-v2 into master
Reviewed-on: urdt/ussd#256
2025-01-08 13:30:39 +01:00
b698f08136
chore: add space after punctuation 2025-01-08 15:27:10 +03:00
4d7589ad95 Merge branch 'master' into lash/purify-more 2025-01-08 13:07:50 +01:00
efdb52bccd
chore: add space after punctuation 2025-01-08 14:54:58 +03:00
2ff9fed3c5
chore: rename countIncorrectPINAttempts to incrementIncorrectPINAttempts 2025-01-08 14:54:57 +03:00
477b4cf8f6
chore : rename remainingPINAttempts to currentWrongPinAttemptsCount 2025-01-08 14:54:57 +03:00
ed6651697a
chore : add variable description to AllowedPINAttempts 2025-01-08 14:54:56 +03:00
c359d99075 Merge branch 'master' into account-pin-block-v2 2025-01-08 10:00:46 +01:00
8d477356f3
update tests 2025-01-08 11:47:55 +03:00
7f3294a8a2
update tests 2025-01-08 11:47:41 +03:00
4b5f08e25e
Merge branch 'master' into postgres-switch-for-tests 2025-01-08 11:06:15 +03:00
ea9cab930e
cleanup the generated test data for the schema 2025-01-08 10:59:22 +03:00
a37f6e6da3
pass the dbschema in the context 2025-01-08 10:57:58 +03:00
f59c3a53ef
allow the BuildConnStr to be accessed by different packages 2025-01-08 10:56:59 +03:00
81c3378ea6
use a flag to pass the schema to the context 2025-01-08 10:55:43 +03:00
46a6d2bc6e
create a schema if it does not exist and use it in the connection 2025-01-08 10:37:47 +03:00
lash
721f80d0f2
Repalce missing context 2025-01-08 07:34:22 +00:00
f49e54a562 Merge pull request 'Space after comma' (#259) from lash/helpcomma into master
Reviewed-on: urdt/ussd#259
2025-01-08 07:57:18 +01:00
lash
5081b6d4ce
Space after comma 2025-01-08 06:48:35 +00:00
4d72ae0313
add handler showing a message for a blocked account 2025-01-08 09:30:51 +03:00
4fe64a7747
show message for a blocked account 2025-01-08 09:29:00 +03:00
3004698d5b
add a message for a blocked account 2025-01-08 09:28:31 +03:00
50c7ff1046
register handler to show blocked account message 2025-01-08 09:27:45 +03:00
07b061a68b
remove blocked account templates 2025-01-08 09:26:53 +03:00
6339f0c2e5 Merge branch 'master' into lash/purify-more 2025-01-07 17:58:19 +01:00
lash
1fa830f286
Add auth conn string to ssh, use connstr for execs 2025-01-07 13:51:26 +00:00
64fba91670
catch blocked account 2025-01-07 14:38:44 +03:00
c15958a1ad
reset incorrect pin attempts on correct entry 2025-01-07 14:32:44 +03:00
ee442daefa
add blocked account node 2025-01-07 14:03:53 +03:00
656052dc74 Merge pull request 'trim any leading whitespace in the input' (#258) from send-input-fix into master
Some checks failed
release / docker (push) Has been cancelled
Reviewed-on: urdt/ussd#258
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2025-01-07 10:33:20 +01:00
6c5873da6f
trim any leading whitespace in the input 2025-01-07 12:15:15 +03:00
11d30583a4
map content of reset_incorrect and catch blocked account 2025-01-07 10:50:30 +03:00
f83f539046
add node to show remaining pin attempts 2025-01-07 10:48:59 +03:00
562bd4fa24
check for incorrect pin 2025-01-06 22:54:31 +03:00
90df0eefc3
add value for allowed number of PIN attempts 2025-01-06 22:53:59 +03:00
b37f2a0a11
add flag for when an account has been blocked 2025-01-06 21:06:54 +03:00
68e4c9af03
add key for incorrect pin attempts 2025-01-06 21:00:34 +03:00
c12e867ac3
add a db flag to specify the database of choice 2025-01-06 15:06:25 +03:00
79de0a9092
pass the base directory to load the .env file 2025-01-06 14:54:04 +03:00
3ee15497a5
specify the base directory for loading the .env file 2025-01-06 14:50:39 +03:00
lash
e09e324a50 Merge branch 'lash/purify-more' into lash/purify-max 2025-01-06 09:03:30 +00:00
lash
599815c343
Fix remaining conflict in cmd cli 2025-01-06 09:00:41 +00:00
lash
462c0d7677 Merge branch 'master' into lash/purify-more 2025-01-06 08:59:42 +00:00
80b96e9bf6 Merge pull request 'Add gettext capability to template and menu resources' (#239) from lash/gettext into master
Reviewed-on: urdt/ussd#239
2025-01-06 09:49:53 +01:00
b5561decd1 Merge branch 'master' into lash/gettext 2025-01-06 09:48:33 +01:00
lash
02823fd64e Merge branch 'lash/ssh-fixes' into lash/purify-more 2025-01-06 08:47:49 +00:00
lash
cd575c2edb Merge remote-tracking branch 'urdt' into lash/purify-more 2025-01-06 08:46:01 +00:00
f3d4f35718 Merge pull request 'Factor out db dump formatting' (#243) from lash/dump-format into master
Reviewed-on: urdt/ussd#243
2025-01-06 09:44:29 +01:00
52787bdb4d Merge branch 'master' into lash/dump-format 2025-01-06 09:42:26 +01:00
lash
f8d8f265f1
Merge upstream 2025-01-06 08:40:50 +00:00
lash
9371b52f3e Merge branch 'lash/ssh-fixes' into lash/purify-max 2025-01-06 08:39:40 +00:00
lash
563000ec15 Merge branch 'lash/purify-more' into lash/purify-max 2025-01-06 08:38:05 +00:00
824d39908b
ci: fix missing ssh dir 2025-01-06 11:19:36 +03:00
lash
52fd1eced2
Enable env, config, db in ssh 2025-01-06 08:11:37 +00:00
a312ea5b84
feat: inject build string in ssh binary, expose default ssh port 2025-01-06 11:09:51 +03:00
lash
5c7a535288 Merge branch 'lash/purify-more' into lash/ssh-fixes 2025-01-06 07:55:40 +00:00
4836162f40
ci: add ssh build 2025-01-06 10:51:20 +03:00
lash
cc2f7b41df Merge branch 'master' into lash/purify-more 2025-01-06 07:50:55 +00:00
lash
d39740a09a
Edit ssh cli help text 2025-01-06 07:41:24 +00:00
lash
2024cc96e2
Bring up-to-date with refactor 2025-01-06 07:22:58 +00:00
lash
d2d878d5d7 Merge branch 'master' into lash/ssh-4 2025-01-06 07:12:00 +00:00
c995143543 Merge pull request 'log-session-id-at-sessionid' (#251) from log-session-id-at-sessionid into master
Reviewed-on: urdt/ussd#251
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2025-01-06 08:01:20 +01:00
44570e20ef
remove unused context key :- at-session-id 2025-01-06 09:59:47 +03:00
362eb209ef
add SessionId to context key 2025-01-06 09:54:28 +03:00
c69d3896f1
pass context as an argument,rename context keys 2025-01-06 08:52:53 +03:00
974af6b2a7
pass context as an argument 2025-01-06 08:50:53 +03:00
lash
bb4037e73f
Add languages env example 2025-01-05 21:25:09 +00:00
lash
739fd90dfd
Expose httpmocks 2025-01-05 21:04:21 +00:00
lash
6789c4f550
Export handlers 2025-01-05 11:17:58 +00:00
lash
437f73827d
Rehabilitate all tets 2025-01-05 09:54:19 +00:00
lash
f0a4a0df61
Correct package name in errors, add state store getter 2025-01-05 07:19:25 +00:00
lash
bd604219b8
WIP Factor out request, errors 2025-01-04 22:27:46 +00:00
lash
51b6fc0dde
Remove unused methods in storage interfaces, improve logs 2025-01-04 21:13:39 +00:00
lash
cc9760125a
Remove unnecessary connection chain step 2025-01-04 21:02:08 +00:00
lash
3a9f3fa373
Update env example 2025-01-04 20:54:51 +00:00
lash
89c21847b9
Improve error message 2025-01-04 20:52:49 +00:00
lash
450dfa02cc
Refactor to use conndata as menustorageservice conn arg 2025-01-04 20:36:18 +00:00
lash
f61e65f4fe
Rename accountservice testservice source file 2025-01-04 13:24:14 +00:00
lash
a4d6cef9c0
Remove commented code 2025-01-04 13:21:31 +00:00
lash
2992f7ae8e
Update executables with new conn str 2025-01-04 13:19:30 +00:00
lash
dc61d05584
WIP revert connstr gdbm to dir only, add file as table spec 2025-01-04 12:16:28 +00:00
lash
83857026d3 Merge branch 'master' into lash/dump-format 2025-01-04 10:00:25 +00:00
lash
349051b5ef Merge branch 'master' into lash/gettext 2025-01-04 09:59:26 +00:00
47b5ff0435 Merge pull request 'Improve separation of concerns in all modules, phase 1' (#246) from lash/purify into master
Reviewed-on: urdt/ussd#246
2025-01-04 10:56:17 +01:00
lash
e92e498726 Merge branch 'lash/purify' into lash/purify-more 2025-01-04 09:46:18 +00:00
lash
25867cf05e
Rehabilitate voucher test 2025-01-04 09:42:36 +00:00
lash
c3cbe1cd92
Add connstr to last executable 2025-01-04 09:41:24 +00:00
lash
418080d093 Merge branch 'lash/purify' into lash/purify-more 2025-01-04 09:38:23 +00:00
lash
2e30739ec9
Implement connstr 2025-01-04 09:37:12 +00:00
d5a2680500
make context accessible 2025-01-04 12:02:45 +03:00
lash
dc1674ec55
WIP add connection string parser 2025-01-04 08:40:43 +00:00
lash
d950b10b50
Move prefix db spec to separate package 2025-01-04 08:37:28 +00:00
lash
bcb3ab905e
Move db related to own package 2025-01-04 08:09:18 +00:00
lash
3ed9caf16d
Factor out request parsers 2025-01-04 08:02:44 +00:00
lash
86464c31d2 Merge branch 'master' into lash/purify 2025-01-04 07:57:54 +00:00
5ee10d8e14 Merge pull request 'logs-at-sessionid' (#245) from logs-at-sessionid into master
Some checks failed
release / docker (push) Has been cancelled
Reviewed-on: urdt/ussd#245
2025-01-04 08:56:09 +01:00
62f3681b9e
define context keysessionid using go-vise --withcontext 2025-01-04 10:40:26 +03:00
3ce1435591
extract session id from africastalking request 2025-01-04 10:38:25 +03:00
f65c458daa
update go-vise. 2025-01-04 10:35:59 +03:00
lash
67007fcd48
Factor out gdbm package 2025-01-04 07:35:28 +00:00
lash
f1b258fa6d
Factor out at code 2025-01-04 07:29:22 +00:00
lash
daec816a3e
Move store devtools location 2025-01-03 17:21:52 +00:00
lash
ac0c43cb43
Factor out formatting method 2025-01-03 17:18:23 +00:00
lash
9013cc3618
Improve error messages 2025-01-03 15:10:20 +00:00
lash
056d056613
Add language source and template file generator 2025-01-03 14:43:08 +00:00
lash
e581ec4771 Merge tag 'v0.8.0-beta.4' into lash/gettext 2025-01-03 10:29:17 +00:00
lash
e16b7445e8
Move arg var to same spot as other runners 2025-01-03 10:28:27 +00:00
lash
1b12f0ba5f
Add po language alternative to all runners 2025-01-03 10:00:52 +00:00
d2fce05461 Merge pull request 'fix: language change' (#242) from language-change-fix into master
Some checks failed
release / docker (push) Has been cancelled
Reviewed-on: urdt/ussd#242
2025-01-03 09:30:27 +01:00
68ac237449 Merge branch 'master' into language-change-fix 2025-01-03 09:28:48 +01:00
162e6c1934
fix: language change 2025-01-03 11:26:56 +03:00
8bd025f2b2 Merge pull request 'hash-pin' (#235) from hash-pin into master
Some checks failed
release / docker (push) Has been cancelled
Reviewed-on: urdt/ussd#235
2025-01-03 09:25:26 +01:00
9d6e25e184
revert to previous state for the adminstore 2025-01-03 11:24:24 +03:00
c26f5683f6
removed second unused argument 2025-01-03 11:17:09 +03:00
91dc9ce82f
tests: add sample pin/hash pair from migration dataset 2025-01-03 11:10:07 +03:00
0fe48a30fa
Merge branch 'master' into hash-pin 2025-01-03 06:58:41 +03:00
lash
c1e0617bb3
Update go-vise 2025-01-02 21:13:06 +00:00
lash
6723884103
Update go-vise 2025-01-02 21:02:01 +00:00
lash
b888af446d
update govise 2025-01-02 18:49:16 +00:00
lash
43b2c3b78d
Rehabilitate gettext resource 2025-01-02 18:13:37 +00:00
lash
d67853f6d9 Merge branch 'master' into lash/gettext 2025-01-02 14:53:18 +00:00
58edfa01a2 Merge pull request 'menu-primary-selectors' (#237) from menu-primary-selectors into master
Some checks failed
release / docker (push) Has been cancelled
Reviewed-on: urdt/ussd#237
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2025-01-02 15:50:42 +01:00
3830c12a57
update tests 2025-01-02 17:42:03 +03:00
f1fd690a7b
update expected content 2025-01-02 17:37:26 +03:00
lash
06230dc557
Add todo comment 2025-01-02 14:31:13 +00:00
491b7424a9
point to the correct ./devtools/admin_numbers directory 2025-01-02 16:01:19 +03:00
29ce4b83bd
added tests for HashPIN and VerifyPIN 2025-01-02 15:22:07 +03:00
ca8df5989a
updated expected age in test 2025-01-02 15:15:52 +03:00
82b4365d16
hash the PIN in TestAuthorize 2025-01-02 14:38:22 +03:00
98db85511b
hash the PIN in the ResetOthersPin function 2025-01-02 14:37:45 +03:00
99a4d3ff42
verify the PIN input against the hashed PIN 2025-01-02 13:51:57 +03:00
d95c7abea4
return if the PIN is not a match, and hash the PIN before saving it 2025-01-02 13:45:18 +03:00
fd1ac85a1b
add code to Hash and Verify the PIN 2025-01-02 13:43:38 +03:00
c899c098f6
updated the expected age 2025-01-02 13:20:01 +03:00
5ca6a74274
move PIN test to the common package 2025-01-02 13:18:49 +03:00
48d63fb43f
added pin.go to contain all PIN related functionality 2025-01-02 13:16:38 +03:00
lash
6ee2c88fe2
Implement gettext spec in local vm cmd 2025-01-02 09:39:49 +00:00
e666c58644
start primary selectors with 1 2025-01-02 12:17:28 +03:00
e980586910
chore: repeat same node on invalid menu choice 2025-01-02 12:15:57 +03:00
ffd5be1f1f
add quit option on view profile 2025-01-02 12:12:52 +03:00
ed1aeecf7d Merge pull request 'Legible dumper' (#232) from lash/dump-key-prefix into master
Some checks failed
release / docker (push) Has been cancelled
Reviewed-on: urdt/ussd#232
2024-12-31 09:56:04 +01:00
3b69f3d38d Merge branch 'master' into lash/dump-key-prefix 2024-12-31 09:55:40 +01:00
lash
cd58f5ae33
Upgrade govise 2024-12-31 08:55:25 +00:00
7a535f796a
output the value as a string 2024-12-31 11:41:04 +03:00
7c4c73125e Merge pull request 'force-restart-state' (#223) from force-restart-state into master
Reviewed-on: urdt/ussd#223
2024-12-31 09:34:44 +01:00
lash
c7dbe1d88f
Remove obsolete subprefix strings 2024-12-31 08:30:08 +00:00
4ea52bf3fb
removed unused code 2024-12-31 11:16:43 +03:00
be2ea3a2f0
removed the non-working restart_state devtool 2024-12-31 10:51:29 +03:00
8217ea8fdc Merge branch 'master' into force-restart-state 2024-12-31 05:06:26 +03:00
3c73fc7188
added a test for the Init func with the different states 2024-12-31 05:05:39 +03:00
1311a0cab9
use the 'send_with_invite' test group in the menu traversal test 2024-12-31 02:36:28 +03:00
lash
3bcd48e5a7
Update govise 2024-12-30 19:58:34 +00:00
lash
0e12c0ee4e
Add prefix for dumper, format base dump key for pg 2024-12-30 19:35:45 +00:00
3caee98cdb Merge pull request 'mixed-languages' (#228) from mixed-languages into master
Reviewed-on: urdt/ussd#228
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2024-12-30 09:07:13 +01:00
db7c9bf56d
chore: add colon to enhance formatting. 2024-12-30 08:07:39 +03:00
0a332ec501
chore: ensure swahili language translation. 2024-12-30 08:05:36 +03:00
90367fe53e Merge pull request 'profile-update-fix' (#226) from profile-update-fix into master
Reviewed-on: urdt/ussd#226
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2024-12-28 16:20:32 +01:00
50c006546c
added code to reset the state and persist it 2024-12-28 13:21:03 +03:00
e8c171a82e Merge branch 'master' into force-restart-state 2024-12-28 11:46:15 +03:00
58a60f2c81
update expected age in test 2024-12-28 08:51:38 +03:00
0820e1b9f2 Merge branch 'master' into profile-update-fix 2024-12-28 06:30:14 +01:00
46edf2b819
remove
redundant catch on pin entry
2024-12-27 16:13:36 +03:00
11eb61ba35
repeat same node on invalid selection 2024-12-27 16:11:09 +03:00
813b92af78 Merge pull request 'issue-205: added comments for menu handlers methods.' (#218) from konstantinmds/ussd:dev/issue-205 into master
Reviewed-on: urdt/ussd#218
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2024-12-27 12:58:00 +01:00
5579991d66
guard profile update after being set 2024-12-27 10:07:05 +03:00
f4f4fdd3ac issue-205:
added comments for menu handlers methods and changed function name to better fit function workings.
2024-12-25 15:59:28 +01:00
be215d3f75
set the code to an empty byte for it to move to the top node 2024-12-20 12:26:07 +03:00
235af3519d Merge pull request 'add-space-after-colon' (#211) from add-space-after-colon into master
Some checks failed
release / docker (push) Has been cancelled
Reviewed-on: urdt/ussd#211
2024-12-19 11:35:13 +01:00
1292851226
rename the function to ReplaceSeparatorFunc 2024-12-19 13:32:39 +03:00
dfd0a0994b Merge branch 'master' into force-restart-state 2024-12-18 22:39:20 +03:00
97fcdda12f
Merge branch 'master' into add-space-after-colon 2024-12-18 22:30:41 +03:00
055c2db790
use a common mockReplaceSeparator func 2024-12-18 22:25:47 +03:00
ecfdab47a8
updated test 2024-12-18 22:21:52 +03:00
fda68231ea
use the replaceSeparator func to format the generated menus 2024-12-18 21:59:09 +03:00
d08afff443
add the replaceSeparator func and pass it to the Handler struct 2024-12-18 21:56:37 +03:00
17ba6a06ba
remove the MenuSeparator from the context 2024-12-18 21:49:42 +03:00
dbd59a4023 Merge pull request 'add link to terms page' (#217) from link-terms-and-conditions into master
Reviewed-on: urdt/ussd#217
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2024-12-18 07:45:48 +01:00
5534706189
reset the state when input is nil 2024-12-17 17:58:08 +03:00
5428626c3f
cleaned up the restart_state 2024-12-17 17:56:56 +03:00
9b33117cb1
add space on expected content 2024-12-17 16:02:35 +03:00
70b2fa4ac2
add spacing after link 2024-12-17 15:46:28 +03:00
fd6ff86579
add link to terms and conditions as expected content 2024-12-17 15:24:15 +03:00
549782f230
add link to terms page 2024-12-17 15:12:38 +03:00
8cf4848b45 Merge pull request 'Userstore dumper tool' (#153) from lash/store-dumper into master
Some checks failed
release / docker (push) Has been cancelled
Reviewed-on: urdt/ussd#153
2024-12-14 13:02:48 +01:00
9f6c0a1111 Merge branch 'master' into lash/store-dumper 2024-12-14 13:02:38 +01:00
lash
1ab49647f6
Upgrade vise 2024-12-14 12:02:13 +00:00
lash
8d4d8a48e0
Fix compile errors, test errors 2024-12-14 11:56:31 +00:00
7aea2af9a1
updated tests 2024-12-13 11:44:04 +03:00
5cd791aae7
use the MenuSeparator 2024-12-13 11:43:47 +03:00
df5e5f1a4b
properly format the vouchers 2024-12-13 11:40:39 +03:00
64c1fe5276
set the separator as a var and add it to the context 2024-12-13 11:38:10 +03:00
f38ea59569
set the separator as a config and not an arg 2024-12-13 01:10:46 +03:00
6cc285d1e8
add the custom separator to the menu 2024-12-12 21:12:25 +03:00
0d7f7aaca1
use latest commits from go-vise 2024-12-12 21:09:48 +03:00
f8ea2daa73
initialize the restart state devtool 2024-12-12 19:55:01 +03:00
lash
c820e89cb7
Segment tx userdata types, add internals docs 2024-12-11 19:13:13 +00:00
e05f8e7291
update to the latest go-vise changes 2024-12-11 19:46:52 +03:00
2383e8ead3
updated failed menuhandler_test 2024-12-11 19:35:04 +03:00
1a4ee0d3e1
updated the description of the GetTransactionsList function 2024-12-11 19:32:41 +03:00
6f3b30e2fe
Capitalize statement details and add a space after the colon 2024-12-11 19:31:17 +03:00
b1e4b63c6a
Add a space after the colon for vouchers 2024-12-11 19:28:53 +03:00
3129e8210e
Capitalize the transfer statement details 2024-12-11 19:25:38 +03:00
5d8de80a18
Write the error in the response 2024-12-11 18:58:50 +03:00
lash
604c16ec90
Habilitate store dumper 2024-12-08 22:48:39 +00:00
lash
a3e821fb16
Clarify gen cmd example with reverse public key lookup 2024-12-08 21:57:53 +00:00
lash
890f50704f
Add documentation comments for db subprefix types 2024-12-08 21:21:48 +00:00
lash
3416fdf50c
Add keyinfo restore 2024-12-07 23:06:03 +00:00
43892f0d8c Merge pull request 'profile-edit-traverse' (#199) from profile-edit-traverse into master
Some checks failed
release / docker (push) Has been cancelled
Reviewed-on: urdt/ussd#199
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2024-12-05 16:37:37 +01:00
8e6b1e6f52
Merge branch 'master' into profile-edit-traverse 2024-12-05 18:34:29 +03:00
lash
ff943a125c Merge branch 'master' into lash/store-dumper 2024-12-05 15:30:29 +00:00
9cbbdff993
chore: use profileDataKeys as an array 2024-12-05 18:25:51 +03:00
316358765d Merge pull request 'data-items-cleanup' (#203) from data-items-cleanup into master
Reviewed-on: urdt/ussd#203
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2024-12-05 16:03:50 +01:00
14737b5f12
Removed redundant naming of transfer related data 2024-12-05 17:58:51 +03:00
caff27b43d
Replace IntToBytes(value int) and ToBytes() with a single ToBytes() function 2024-12-05 17:50:40 +03:00
589a94216b
Use the DATATYPE_USERDATA as the prefix for the NewSubPrefixDb func 2024-12-05 17:02:26 +03:00
a659fb06fa
Added a function to convert int to []byte 2024-12-05 16:58:03 +03:00
f733fe5636
Start the sub prefix data at 256 (0x0100) 2024-12-05 16:31:47 +03:00
18423fcd9c
updated the name of the voucher related data 2024-12-05 16:26:56 +03:00
72a3681767
add test data. 2024-12-05 16:03:08 +03:00
160ccbb220
read test file from test run arg 2024-12-05 14:05:32 +03:00
22f96363ba
add test files 2024-12-05 14:04:56 +03:00
3e7f90733e
update test names 2024-12-05 12:22:29 +03:00
321f038c7c
iterate over a map for the set profile items 2024-12-05 10:52:45 +03:00
7a9de79aae
return nil with error 2024-12-04 21:07:11 +03:00
862830e9de
renamed internal/storage/db.go -> internal/storage/sub_prefix_db.go for clarity 2024-12-04 20:59:46 +03:00
bc0e536d3d
updated failing tests 2024-12-04 20:55:03 +03:00
82884a75a3
Merge branch 'master' into data-items-cleanup 2024-12-04 20:45:38 +03:00
93c44861e0
Use numeric prefixes 2024-12-04 20:42:47 +03:00
4ecfc9de38
removed DATATYPE_USERSUB and replaced with DATATYPE_USERDATA 2024-12-04 20:38:52 +03:00
a84c3e0852
update menu traversal test data 2024-12-04 09:46:16 +03:00
8efed966a0
set flag when location is set 2024-12-04 09:08:47 +03:00
e7c4b5bca7
update tests 2024-12-04 09:08:25 +03:00
ed632248c5
add doc lines and check for back naviagtions 2024-12-04 08:30:07 +03:00
5c202741d6
add handler for catching back navigations 2024-12-04 08:20:43 +03:00
c5ebdbf85b
catch back navigations 2024-12-04 08:20:09 +03:00
c4282a870e
add flag to catch back navigations 2024-12-04 08:19:20 +03:00
91cd6077ce
Merge branch 'master' into profile-edit-traverse 2024-12-03 22:25:47 +03:00
c0ed6fa9c8
catch incorrect pin entries 2024-12-03 21:43:24 +03:00
22c9c3e0f0 Merge pull request 'minor-bug-fixes' (#177) from minor-bug-fixes into master
Reviewed-on: urdt/ussd#177
2024-12-03 18:18:23 +01:00
a709d24520 Merge branch 'master' into minor-bug-fixes 2024-12-03 18:16:19 +01:00
e56138e416 Merge pull request 'Clear persister from handler in outer code aswell' (#200) from lash/persister-freakout into master
Reviewed-on: urdt/ussd#200
2024-12-03 17:18:11 +01:00
lash
d516584d90
Clear persister from handler in outer code aswell 2024-12-03 16:16:53 +00:00
b420a9bba0
set flag if profile data is set 2024-12-03 17:41:06 +03:00
a20ab79355
explicit reload save gender 2024-12-03 17:38:20 +03:00
e0ec15b272
allow sequential profile edit 2024-12-03 14:40:57 +03:00
9e998f9a29
add a zero pad value to unfilled profile item 2024-12-03 14:37:55 +03:00
1c7c0af712
catch next unset profile item 2024-12-03 14:36:48 +03:00
d40a4a171f
formatted code 2024-12-03 14:12:47 +03:00
ba430a5849
add a separate function to handle ConstructName 2024-12-03 14:10:05 +03:00
0f21b01813
resolved error in the TestViewVoucher 2024-12-03 13:37:00 +03:00
10586baf0d
resolved error in the TestCheckBalance 2024-12-03 13:35:14 +03:00
e979742424
resolved error in the TestValidateRecipient 2024-12-03 13:32:18 +03:00
ff3f049226
updated the CheckAliasAddress mock 2024-12-03 13:31:30 +03:00
13b45c49da Merge branch 'master' into minor-bug-fixes 2024-12-03 12:58:26 +03:00
a72fb08dc8
allow sequential profile edit 2024-12-03 11:20:35 +03:00
944fa89b3c
add profile holder struct 2024-12-03 11:19:38 +03:00
48e1b02e0e
allow all item profile edit 2024-12-02 20:50:21 +03:00
3e0bbe5ffe
add handler to update profile items 2024-12-02 20:35:56 +03:00
fd586d09c3
add required profile edit flags 2024-12-02 20:35:04 +03:00
lash
c2a4efde2b Merge branch 'master' into lash/store-dumper 2024-12-02 15:39:29 +00:00
b615c27cf6 Merge pull request 'trigger-balance-reload' (#193) from trigger-balance-reload into master
Some checks failed
release / docker (push) Has been cancelled
Reviewed-on: urdt/ussd#193
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2024-12-02 16:36:26 +01:00
22e870b3e5 Merge branch 'master' into trigger-balance-reload 2024-12-02 16:36:08 +01:00
da462346f9 Merge pull request 'Always reset persister in handler' (#194) from lash/no-persister-deadlock into master
Reviewed-on: urdt/ussd#194
2024-12-02 16:17:36 +01:00
lash
406bd84875
Always reset persister in handler 2024-12-02 14:53:18 +00:00
lash
c9deca1180
change userdata prefix on subprefix debug 2024-12-02 14:36:33 +00:00
419cd185fc Merge branch 'master' into minor-bug-fixes 2024-12-02 15:25:34 +03:00
7976e237ca Merge pull request 'voucher-details' (#179) from voucher-details into master
Reviewed-on: urdt/ussd#179
Reviewed-by: Alfred Kamanda <alfredkamandamw@gmail.com>
2024-12-02 11:43:30 +01:00
19ec8f0817 Merge branch 'master' into voucher-details 2024-12-02 13:32:32 +03:00
ef3a3d6717
updated the TestGetVoucherDetails 2024-12-02 13:30:33 +03:00
c2019267d1
capitalize the voucher descriptions 2024-12-02 13:26:46 +03:00
0091fbcabb
fix: looped navigation 2024-12-02 09:03:04 +03:00
lash
6d4f3109f8
Consolidate subtyp and typ debug 2024-12-01 23:12:58 +00:00
lash
35cf3a1cd1
Add debug label test, capability debug flag 2024-12-01 18:41:28 +00:00
lash
1a782c1db9
Add debug package 2024-12-01 17:32:06 +00:00
lash
3d2ca606ca Merge branch 'master' into lash/store-dumper 2024-12-01 16:34:10 +00:00
aa7497573e
removed unused code 2024-11-30 15:29:28 +03:00
54c1fe51ef
update the active voucher data when checking the current vouchers 2024-11-30 15:28:21 +03:00
7a86b2ad3b
updated the UpdateVoucherData description 2024-11-30 15:26:13 +03:00
6b23c284e5
check vouchers before checking the balance 2024-11-30 15:24:14 +03:00
aab6660edd
Capitalize menu items 2024-11-29 15:39:27 +03:00
c46f41e25f
Format the balance to 2 decimal places 2024-11-29 14:47:22 +03:00
00c0445eed
show name without depending on family name being set 2024-11-28 11:42:47 +03:00
c8c6b05b8a Merge branch 'master' into minor-bug-fixes 2024-11-26 15:31:45 +03:00
08ff1056d7 Validate aliases, addresses and phone numbers in the send menu (#176)
Some checks failed
release / docker (push) Has been cancelled
- Update the phone number regex
- Check whether the recipient is a valid phone number, alias or address

Reviewed-on: urdt/ussd#176
Co-authored-by: alfred-mk <alfredmwaik@gmail.com>
Co-committed-by: alfred-mk <alfredmwaik@gmail.com>
2024-11-26 07:24:57 +01:00
0f4a7e900f Merge pull request 'feat: upgrade go-vise dep, minor cleanups to go.mod' (#182) from sohail/upgrade-deps into master
Reviewed-on: urdt/ussd#182
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2024-11-26 07:02:07 +01:00
2d6c434bde
feat: upgrade go-vise dep, minor cleanups to go.mod
* added stub for Dump()
2024-11-25 09:56:24 +03:00
f5d2644031 Merge pull request 'account-statement' (#126) from account-statement into master
Reviewed-on: urdt/ussd#126
2024-11-22 19:24:08 +01:00
09b4fa2860 Merge branch 'master' into account-statement 2024-11-22 19:23:59 +01:00
a748c1b6b2
chore: fix old reference 2024-11-22 11:53:13 +03:00
a17cf78d29
Merge remote-tracking branch 'refs/remotes/origin/minor-bug-fixes' into minor-bug-fixes 2024-11-22 11:35:57 +03:00
9847433e0a
use _ for back navigation 2024-11-22 11:30:13 +03:00
7ce50398d1
use the language translation instead of hardcoded eng 2024-11-21 15:54:00 +03:00
e30bc177e9
fixed typo and added a new translation 2024-11-21 15:52:07 +03:00
b9ff467c0c
use the correct balance 2024-11-21 15:51:04 +03:00
1174500e3f
add test for voucher details 2024-11-21 15:19:36 +03:00
07df450b3c
include labels to define the symbol and balance while selecting a voucher 2024-11-21 15:15:15 +03:00
b8d938d3aa
add voucher details 2024-11-21 13:04:19 +03:00
d1e9340ea9
add voucher details 2024-11-21 13:03:43 +03:00
8925e26c4c
refactor check for valid yob 2024-11-21 11:25:47 +03:00
9b89462797
add function to check validity of provided yob 2024-11-21 11:21:16 +03:00
51bad64a51 Merge branch 'master' into account-statement 2024-11-20 19:00:14 +03:00
7880294c6f
set eng as default language 2024-11-20 17:14:25 +03:00
451b15fb6b
explicit set_language reload 2024-11-20 17:13:14 +03:00
d20700ca74
fix size limit error 2024-11-20 16:39:50 +03:00
9cf1cbe425
add swahili translation for catch node 2024-11-20 16:36:18 +03:00
212cd48249
debug: postgres conn string
Some checks failed
release / docker (push) Has been cancelled
2024-11-19 17:53:06 +03:00
7adc0c9c08
fix: Dockerfile to include .env
Some checks failed
release / docker (push) Has been cancelled
2024-11-19 17:25:20 +03:00
0a19a6c48b
fix: github ci spec
Some checks failed
release / docker (push) Has been cancelled
2024-11-19 17:18:13 +03:00
66b5843b0d feat: dockerfile and github based CI build for Africastalking variant (#174)
## Summary

* fixed missing error handler in main
* add injectable build string in main
* add (dynamically linked) docker build
* add github CI workflow
* add extra but useful dev files in dev folder

* closes #93

## Notes

* We'll move to a self-hosted CI runner once it is installed on Gitea.

Reviewed-on: urdt/ussd#174
Co-authored-by: Mohammed Sohail <sohailsameja@gmail.com>
Co-committed-by: Mohammed Sohail <sohailsameja@gmail.com>
2024-11-19 15:15:24 +01:00
df89fe69e1
return to the main node 2024-11-19 17:09:59 +03:00
9498242901
removed debug statement 2024-11-19 16:27:19 +03:00
eab6dbd74c
Check if index is within range 2024-11-19 16:23:35 +03:00
6159686a8e
update function comment 2024-11-19 16:21:55 +03:00
1d82bc2261
added transactions functions 2024-11-19 16:07:28 +03:00
bfcdd79f33
view single statement 2024-11-19 16:04:46 +03:00
d49b68597c
check transactions and catch when none exist 2024-11-19 16:03:54 +03:00
1d9f4fc13e
added statement related flags 2024-11-19 15:50:19 +03:00
6fa0d8e2ff Merge branch 'master' into account-statement 2024-11-19 10:33:09 +03:00
109a2a2020 Merge pull request 'menu-balances' (#173) from menu-balances into master
Reviewed-on: urdt/ussd#173
Reviewed-by: Alfred Kamanda <alfredkamandamw@gmail.com>
2024-11-19 08:18:43 +01:00
bc6d8098f3
updated the failed test 2024-11-19 10:15:34 +03:00
01e75e9217
update test 2024-11-18 17:30:34 +03:00
f2b17880ba
check community and my balance separately 2024-11-18 17:30:09 +03:00
1d4f116079
community balance str 2024-11-18 17:23:59 +03:00
44c52b6ed7
rename fetch_custodial_balances -> fetch_community_balance 2024-11-18 17:23:36 +03:00
454f67b317
show balance based on current voucher 2024-11-18 17:21:04 +03:00
e1506a3dcf
show a placehlolder community balance 2024-11-18 17:20:12 +03:00
b22a4adec1 Merge pull request 'updated send node' (#172) from send-node into master
Reviewed-on: urdt/ussd#172
2024-11-18 14:19:42 +01:00
1ba90a8b78
updated the test 2024-11-16 14:52:24 +03:00
5dd4f2a3fb
scale down the balance according to the decimals 2024-11-16 14:52:02 +03:00
b40ad78294
add the GetVoucherDetails function 2024-11-15 21:03:57 +03:00
11bb194f26
add a struct to access the tokenDetails 2024-11-15 21:03:29 +03:00
c0ccdce0a9
add the voucher details node 2024-11-15 21:02:44 +03:00
7d16b710d8
set the TokenDecimals as int to match the API response 2024-11-15 20:50:07 +03:00
c8fc32a4e7
cleaned up models 2024-11-15 18:50:06 +03:00
baeb5e0ccb
use a single doRequest and updated the structs for TokenHoldings and Transfers 2024-11-15 18:37:20 +03:00
51bf2534b8
use a single bearer token 2024-11-15 18:35:49 +03:00
d3fae34290
modified the send node traversal 2024-11-15 13:24:54 +03:00
1a77092ccb
updated the menuhandler tests 2024-11-15 13:12:30 +03:00
36846c2587
added TestReadTransactionData 2024-11-15 12:13:09 +03:00
222d801ecc
added TestParseAndScaleAmount 2024-11-15 11:49:47 +03:00
1a0b4deab3
added the TransactionData struct to organiza the data 2024-11-15 09:20:19 +03:00
cb13b09291
remove commented code 2024-11-15 08:42:44 +03:00
de5ecc5fe7
add the tokens functionality to the common package 2024-11-14 21:21:04 +03:00
5773305785
parse data and initialize a transaction 2024-11-14 20:10:48 +03:00
7985b20200
added message string for failed transaction 2024-11-14 20:09:50 +03:00
c34906cb1f
added the TokenTransfer functionality and mocks 2024-11-14 20:02:48 +03:00
c10e1a6a1b
added the TokenTransferResponse model 2024-11-14 19:36:30 +03:00
fabcccfa60
added the tokenTransfer url 2024-11-14 19:35:44 +03:00
f3e3badff6
save the entire voucher data when setting the default voucher 2024-11-14 17:31:17 +03:00
9d2d01e3e2
save the recipient number in DATA_TEMPORARY_VALUE 2024-11-14 17:30:13 +03:00
93df6a6a08
validate recipients and invite valid ones 2024-11-14 14:59:39 +03:00
8c13e44a15 Merge pull request 'profile-edit-show' (#171) from profile-edit-show into master
Reviewed-on: urdt/ussd#171
Reviewed-by: Alfred Kamanda <alfredkamandamw@gmail.com>
2024-11-14 09:27:42 +01:00
345dfbaa21
Merge remote-tracking branch 'refs/remotes/origin/profile-edit-show' into profile-edit-show 2024-11-14 11:01:42 +03:00
381e581e8e
add terminal logs 2024-11-14 11:00:12 +03:00
94d2e8203f
reload verify yob 2024-11-14 10:53:20 +03:00
f9e51618c5
remove extra line 2024-11-14 10:29:22 +03:00
f97ad2a262
use 1 for retry 2024-11-14 10:25:42 +03:00
59b14301ad Merge branch 'master' into profile-edit-show 2024-11-14 10:08:25 +03:00
8b097a4395 Merge pull request 'log directly to the terminal' (#170) from terminal-logs into master
Reviewed-on: urdt/ussd#170
2024-11-14 08:01:59 +01:00
fd2486b5cf
Merge branch 'terminal-logs' into profile-edit-show 2024-11-13 21:04:40 +03:00
f9f25d898b
use logg 2024-11-13 19:00:27 +03:00
b6b3ef83a4
updated the comment to match the functionality 2024-11-13 18:02:02 +03:00
d7232a53ef
use the bearer token 2024-11-13 16:16:32 +03:00
047bf0e12e
updated the env example 2024-11-13 16:15:37 +03:00
09f61eb64d
log all errors from the hander 2024-11-13 15:19:45 +03:00
abdb17640b
add terminal logs 2024-11-12 10:36:08 +03:00
9af7b775a7
log directly to the terminal 2024-11-11 16:32:17 +03:00
97741b113b
Merge branch 'master' into profile-edit-show 2024-11-11 11:03:01 +03:00
0bb444cd50 Merge pull request 'updated README' (#169) from readme-documentation into master
Reviewed-on: urdt/ussd#169
2024-11-08 22:23:57 +01:00
1d07d7fb1d
updated README 2024-11-08 20:35:17 +03:00
a3e5aab6c4 Merge pull request 'Africastalking POST route' (#168) from africastalking-endpoint into master
Reviewed-on: urdt/ussd#168
2024-11-08 17:25:46 +01:00
9ebfb643aa
remove unused import 2024-11-08 17:28:20 +03:00
0aad21a52c
Merge branch 'master' into profile-edit-show 2024-11-08 17:21:27 +03:00
68d1628546
replace - with: Not provided 2024-11-08 17:19:41 +03:00
f4f95b3292
add some spacing 2024-11-08 17:15:27 +03:00
574807d254
set the africastalking POST route using env 2024-11-08 16:52:19 +03:00
256ed6491b Merge pull request 'http-logs' (#167) from http-logs into master
Reviewed-on: urdt/ussd#167
2024-11-08 12:51:30 +01:00
7a02ffcf0c Merge pull request 'log-file' (#166) from log-file into http-logs
Reviewed-on: urdt/ussd#166
2024-11-08 08:09:15 +01:00
dcd8fce59a
add log on create account 2024-11-08 10:07:06 +03:00
64a7b49218
Remove unused Warning logger 2024-11-08 00:21:11 +03:00
1bcbb2079e
Removed unused variable 2024-11-08 00:17:02 +03:00
e63468433e
Merge branch 'http-logs' into log-file 2024-11-08 00:14:34 +03:00
9c972ffa6b
add specific log files per binary 2024-11-07 16:46:12 +03:00
a11776e1b3
ignore .log files 2024-11-07 16:41:38 +03:00
6ac9ac29d8
add simple http logging 2024-11-07 16:41:08 +03:00
fc8915ea33
add http logging 2024-11-07 16:35:58 +03:00
cc36ddcb6d
add handler for showing the currently set profile information 2024-11-07 12:02:03 +03:00
f3388aef31
use _ for back 2024-11-07 11:59:12 +03:00
4e170b25e2
show currently set profile information 2024-11-07 11:58:58 +03:00
3e258a35fa
show currently set profile information 2024-11-07 11:58:25 +03:00
f66609bbae
add helper for getting db key from string 2024-11-07 09:18:11 +03:00
ebdc7b200a
register handler for getting current profile information 2024-11-07 09:16:49 +03:00
29e1e912d7
use edit prefix on each profile edit node 2024-11-06 17:52:22 +03:00
308f3327d0
use edit prefix on each profile edit information 2024-11-06 17:48:50 +03:00
46b2b354fd Merge pull request 'swahili-templates-menu' (#158) from swahili-templates-menu into master
Reviewed-on: urdt/ussd#158
Reviewed-by: Alfred Kamanda <alfredkamandamw@gmail.com>
2024-11-05 11:29:07 +01:00
7676cfd40c
Merge branch 'master' into swahili-templates-menu 2024-11-05 13:25:49 +03:00
4e350aa25a
update test data file 2024-11-05 10:49:08 +03:00
584d02db29 Merge branch 'master' into lash/store-dumper 2024-11-05 00:19:06 +01:00
859de0513a Merge pull request 'api-error-fix' (#161) from api-error-fix into master
Reviewed-on: urdt/ussd#161
2024-11-05 00:18:04 +01:00
266d3d06c3
Check the flag_no_active_voucher before proceeding 2024-11-04 17:56:25 +03:00
92ea3df4aa
Removeearly return statement 2024-11-04 17:38:55 +03:00
c46c31ea36
ensure swahili translation 2024-11-04 16:06:33 +03:00
5937c6bf5c Merge branch 'master' into lash/store-dumper 2024-11-04 13:56:44 +01:00
da91eed9d4
add retry menu option 2024-11-04 15:55:58 +03:00
e2b28a31b2 Merge pull request 'lash/export-to-term' (#157) from lash/export-to-term into master
Reviewed-on: urdt/ussd#157
2024-11-04 13:54:58 +01:00
88b50c5dd7
Remove admin number defination in env example 2024-11-04 15:52:03 +03:00
43a1208cce
Merge branch 'master' into lash/export-to-term 2024-11-04 15:38:53 +03:00
2b865a365b
add back option to view address 2024-11-04 15:24:51 +03:00
c77558689a
ensure swahlili menu template 2024-11-04 15:24:22 +03:00
a9641fd70d
ensure swahili menu template 2024-11-04 15:24:01 +03:00
lash
2c30ccc405
Add voucherdata call to test accountservices 2024-11-04 02:23:30 +00:00
lash
7189235bee
Remove unused data type 2024-11-03 15:14:17 +00:00
lash
0506a8c452
Add voucherdata endpoint 2024-11-03 14:34:26 +00:00
lash
a237b615f2
Export models package 2024-11-03 01:44:57 +00:00
lash
dae12ac498
Separate subprefix db export 2024-11-02 23:41:08 +00:00
lash
1d77ad98dc
Expose subprefix db 2024-11-02 23:33:52 +00:00
lash
10b3083647
WIP Add db dumper tool 2024-11-02 20:29:32 +00:00
lash
3a8a5f40ba
Add test service placeholders for fetchtransactions 2024-11-02 16:42:50 +00:00
lash
14bc11f4bd
Add transaction getter 2024-11-02 16:38:29 +00:00
lash
e29a24b376
Add missing models files 2024-11-02 15:46:46 +00:00
lash
35a090ef42 Merge branch 'pre-mock-remove' into lash/export-to-term 2024-11-02 14:00:16 +00:00
2587882eae Merge pull request 'pin-reset' (#139) from pin-reset into pre-mock-remove
Reviewed-on: urdt/ussd#139
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2024-11-02 14:54:19 +01:00
24d4b8478e Merge pull request 'Remove db mocks' (#152) from remove-db-mocks into master
Reviewed-on: urdt/ussd#152
2024-11-02 13:44:03 +01:00
476a69fe1b
Update menuhandler tests to use the memdb instead of dbmocks 2024-11-02 03:22:33 +03:00
c52f8312e4
Remove the dbmock and userdbmock 2024-11-02 03:21:38 +03:00
6dbe74d12b
use single temporary value 2024-11-01 16:46:09 +03:00
332074375a
wrap in devtools/admin 2024-11-01 16:44:54 +03:00
5e4a9e7567
Merge branch 'master' into pin-reset 2024-11-01 16:26:29 +03:00
cfe3e526df
Remove the subprefixdbmock 2024-11-01 13:17:45 +03:00
eb2c73dce1
remove unused setadmin store 2024-11-01 11:51:50 +03:00
7e448f739a
change fs store path to root 2024-11-01 09:35:48 +03:00
0014693ba8
remove guard pin option 2024-11-01 06:39:37 +03:00
lash
9a528cfd14
Clean up messily failed conflict resolution 2024-11-01 03:17:01 +00:00
lash
8cc46d2782 Merge branch 'master' into lash/export-to-term 2024-10-31 22:58:36 +00:00
45945ae9c5 Merge pull request 'Consolidate temp data storage' (#150) from consolidate-temp-data-storage into master
Reviewed-on: urdt/ussd#150
2024-10-31 23:47:04 +01:00
d7ea8fa651
Use the DATA_TEMPORARY_VALUE for the user data 2024-11-01 01:10:58 +03:00
e75aa2c1f7 Merge branch 'master' into consolidate-temp-data-storage 2024-11-01 00:45:32 +03:00
63eed81d3d
Merge branch 'master' into consolidate-temp-data-storage 2024-11-01 00:44:15 +03:00
f4ca4454ea
use a single DATA_TEMPORARY_VALUE for the PIN and voucher data 2024-11-01 00:42:23 +03:00
lash
bb1a846cb3 Merge remote-tracking branch 'origin/master' into lash/ssh-4 2024-10-31 20:52:09 +00:00
2704069e74
Merge branch 'master' into pin-reset 2024-10-31 21:09:48 +03:00
7d1a04f089
remove from root 2024-10-31 21:01:24 +03:00
53fa6f64ce
define structure of json 2024-10-31 21:01:01 +03:00
7fa38340dd
add command to initialize a list of admin numbers 2024-10-31 21:00:41 +03:00
7aab3cff8c
remove seed 2024-10-31 21:00:16 +03:00
299534ccf1
define seed as a command in the devtool 2024-10-31 20:59:51 +03:00
b2655b7f11
remove seed from executable 2024-10-31 20:59:11 +03:00
5abe9b78cc
attach an admin store for the phone numbers 2024-10-31 20:11:26 +03:00
12825ae08a
setup adminstore in the local handler service 2024-10-31 20:10:46 +03:00
ac0b4b2ed1
pass context 2024-10-31 20:08:30 +03:00
5f666382ab Merge pull request 'profile-update-pin-check' (#149) from profile-update-pin-check into master
Reviewed-on: urdt/ussd#149
2024-10-31 16:06:47 +01:00
ce917d9e89
update tests 2024-10-31 17:05:06 +03:00
3ce25d0e14
Merge branch 'master' into profile-update-pin-check 2024-10-31 16:42:30 +03:00
8fe8ff540b
Merge branch 'master' into pin-reset 2024-10-31 16:38:28 +03:00
0b4bf58107
resolved failing tests due to tempData 2024-10-31 16:31:29 +03:00
lash
4bf56c525f
Export voucher related code 2024-10-31 13:19:44 +00:00
lash
33bba73a65 Merge branch 'master' into lash/export-to-term 2024-10-31 12:45:53 +00:00
074345fcf9 Merge pull request 'voucher-data' (#138) from voucher-data into master
Reviewed-on: urdt/ussd#138
2024-10-31 13:44:18 +01:00
lash
a17150962e Merge remote-tracking branch 'origin/lash/export-to-term' into lash/export-to-term 2024-10-31 12:39:48 +00:00
lash
3ae75b27a5
WIP replaced check account method but traversal crashes 2024-10-31 12:38:31 +00:00
lash
b2d180e8eb
WIP Trying to clean up account status check 2024-10-31 12:15:07 +00:00
e6a369dcdd
remove unused code 2024-10-31 14:44:42 +03:00
lash
b9c56b04ce
Remove obsolete track account status code 2024-10-31 11:43:27 +00:00
b8bbd88078
retain the temporary data for it to be overwritten 2024-10-31 14:26:28 +03:00
d25128287e
update profile information on individual node 2024-10-31 14:21:22 +03:00
c45fcda2f1
remove back option check,protect profile data update 2024-10-31 14:20:04 +03:00
211cc1f775
perform profile update in individual update node 2024-10-31 14:19:12 +03:00
981f7ca4f6
add keys to for holding temporary profile info 2024-10-31 14:14:50 +03:00
05ed236e03
add node to update individual profile information 2024-10-31 14:14:10 +03:00
bab3f673eb
Removed unused model 2024-10-31 14:13:21 +03:00
767a3cd64c
remove pin guard menu option 2024-10-31 09:38:51 +03:00
c4078c5280
remove extra spaces 2024-10-31 09:21:46 +03:00
lash
dc198215b1
Remove commented code 2024-10-31 02:03:29 +00:00
lash
a48170321c
Finish refactor result models 2024-10-31 01:51:36 +00:00
lash
1e638238ed
WIP refactor models usage 2024-10-31 01:28:37 +00:00
lash
4e81e2d869
Adapt voucher changes to package exports 2024-10-30 21:09:45 +00:00
d434194021
catch incorrect pin entry 2024-10-30 23:21:15 +03:00
c6ca3f6be4
fix sink error 2024-10-30 22:32:38 +03:00
8093eae61a
use 0 instead of 1 for back 2024-10-30 21:26:52 +03:00
833d52a558
remove print message 2024-10-30 21:26:11 +03:00
8262e14198
Merge branch 'master' into pin-reset 2024-10-30 21:10:12 +03:00
a31cac4e50
Merge branch 'master' into voucher-data 2024-10-30 18:46:21 +03:00
8b399781e8
make the VoucherMetadata more descriptive 2024-10-30 18:40:03 +03:00
caafe495be
use the dataserviceapi structs 2024-10-30 18:30:55 +03:00
66b34eaea4
get the ussd-data-service package 2024-10-30 18:21:49 +03:00
ea4c6d9314
check for phone number validity 2024-10-30 18:01:43 +03:00
7c823e07ca
move to root node after on back 2024-10-30 18:01:20 +03:00
41585f831c
move catch and load to next node 2024-10-30 18:00:38 +03:00
d93a26f9b0
remove function exec after HALT 2024-10-30 17:58:52 +03:00
lash
ff26ccc545
Expose api interface 2024-10-30 13:09:15 +00:00
lash
72c688b885 Merge branch 'master' into lash/export-to-term 2024-10-30 12:02:37 +00:00
lash
14648fec6c
Edit comment 2024-10-30 12:02:16 +00:00
cf523e30f8
update handler in test 2024-10-30 14:50:31 +03:00
888d3befe9
add actual pin reset functionality 2024-10-30 14:50:12 +03:00
017691a40c
define structure for admin numbers 2024-10-30 14:41:14 +03:00
dc418771a7
attach an admin store for phone numbers 2024-10-30 14:33:48 +03:00
c2068db050
update handler functions 2024-10-30 14:33:22 +03:00
c42b1cd66b
provide required handler functions and admin store 2024-10-30 14:32:01 +03:00
b404ae95fb
setup an admin store based on fs 2024-10-30 14:30:38 +03:00
adaa0c63ef
Extract common db operations for the test 2024-10-30 14:12:42 +03:00
843b0d1e7e Merge pull request 'Add reverse sessionid address lookup' (#146) from lash/reverse-session into master
Reviewed-on: urdt/ussd#146
2024-10-30 10:35:55 +01:00
lash
c95b97cb14
Export user data store 2024-10-30 01:45:38 +00:00
lash
dd764a2e24
Export db datatypes,tools 2024-10-30 01:28:55 +00:00
lash
cb997159f7
Add reverse sessionid address lookup 2024-10-30 00:59:59 +00:00
7241cdbfcb
Updated the tests 2024-10-30 00:53:13 +03:00
0480c02633
Moved voucher related functions to the utils package 2024-10-30 00:52:23 +03:00
0a97f610a4
catch unregistred number 2024-10-29 22:23:22 +03:00
5a0563df94
group regex,check for valid number against the regex 2024-10-29 22:17:43 +03:00
7597b96dae
remove catch for unregistered number 2024-10-29 22:16:34 +03:00
f37483e2f0
use _ for back navigation 2024-10-29 22:15:31 +03:00
d0ad6395b5
add check for unregistered phone numbers 2024-10-29 17:35:42 +03:00
106983a394
use explicit back to node 2024-10-29 17:35:01 +03:00
91b85af11a
add reset unregistered number 2024-10-29 17:34:34 +03:00
534d756318
catch unregistred phone numbers 2024-10-29 17:18:39 +03:00
6998c30dd1
add node to handle unregistered phone numbers 2024-10-29 17:18:01 +03:00
449f90c95b
add flag to catch unregistred numbers 2024-10-29 17:17:03 +03:00
e96c874300
repeat same node on invalid option input 2024-10-29 15:02:40 +03:00
b35460d3c1
Merge branch 'master' into pin-reset 2024-10-29 14:35:17 +03:00
124049c924
add admin number defination in env 2024-10-29 14:32:17 +03:00
5fd3eb3c29
set admin privilege flag 2024-10-29 14:28:58 +03:00
d83962c0ba
load admin numbers defined in the .env 2024-10-29 14:26:24 +03:00
41da099933
remove the admin flag,setup an admin store 2024-10-29 13:24:13 +03:00
c9bb93ede6
create a simple admin store for phone numbers 2024-10-29 13:15:41 +03:00
ca13d9155c
replace _ with explicit back node 2024-10-29 13:15:22 +03:00
e338ce0025
load and reload only after input 2024-10-29 13:14:49 +03:00
03c32fd265 Merge branch 'master' into voucher-data 2024-10-28 18:40:37 +03:00
727f54ee57 Merge pull request 'tests-refactor' (#137) from tests-refactor into master
Reviewed-on: urdt/ussd#137
2024-10-28 16:28:41 +01:00
b97965193b
add pin reset for others handling 2024-10-28 16:37:23 +03:00
aec0abb2b6
setup an admin flag 2024-10-28 16:34:33 +03:00
2c361e5b96
Added tests related to the vouchers list 2024-10-28 16:30:13 +03:00
131f3bcf46
Added the prefixDb to the Handlers struct~ 2024-10-28 16:27:24 +03:00
520f5abdcd
Added the subPrefixDb mock 2024-10-28 16:23:44 +03:00
5d294b663c
Added the PrefixDb interface 2024-10-28 16:21:31 +03:00
26073c8000
define handler functions required to reset others pin 2024-10-28 15:49:20 +03:00
e4c2f644f3
define a key to hold number during pin reset 2024-10-28 15:47:56 +03:00
3de46cef5e
setup pin reset nodes 2024-10-28 15:45:08 +03:00
0cc0bdf9f7
add pin reset for others nodes 2024-10-28 15:19:35 +03:00
72d5c186dd
add admin privilege flag 2024-10-28 15:18:40 +03:00
dc782d87a8
Updated the TestSetVoucher 2024-10-28 11:20:06 +03:00
ddae746b9d
formatted code 2024-10-28 11:07:59 +03:00
4e1b2d5ddb
update account services 2024-10-25 18:01:52 +03:00
d8800a665d
Merge branch 'master' into tests-refactor 2024-10-25 17:48:40 +03:00
6c3ff0e9db Merge branch 'master' into voucher-data 2024-10-25 17:37:08 +03:00
3ef64271e7
Store and retrieve the voucher decimals and contract address 2024-10-25 17:24:09 +03:00
2dee47404d Merge pull request 'menu-voucherlist' (#101) from menu-voucherlist into master
Reviewed-on: urdt/ussd#101
2024-10-25 15:59:46 +02:00
3792bfdc1f
run mod tidy 2024-10-25 09:38:09 +03:00
a0e97cfe5b
remove test account service implementation 2024-10-25 09:37:16 +03:00
a3be98c514
update test account service 2024-10-25 09:36:43 +03:00
2b34b3a75c
Merge branch 'master' into tests-refactor 2024-10-25 09:14:16 +03:00
b4454f7517
Added context to FetchVouchers 2024-10-24 20:44:29 +03:00
d9c660b8ea
Merge branch 'master' into menu-voucherlist 2024-10-24 20:39:43 +03:00
d113ea82fd
Add dynamic send_amount and session_id 2024-10-24 20:21:28 +03:00
a92c640cb7
Updated tests 2024-10-24 18:15:54 +03:00
728815f0c6
Include the active symbol in the send menu 2024-10-24 17:50:37 +03:00
6b5d3f74d1 Merge pull request 'api-context' (#127) from api-context into master
Reviewed-on: urdt/ussd#127
2024-10-24 16:45:37 +02:00
bee9ad5ff5
Merge remote-tracking branch 'refs/remotes/origin/api-context' into api-context 2024-10-24 17:39:11 +03:00
6e7b46666e
ensure mod match with master 2024-10-24 17:34:42 +03:00
383f074cae
update method signatures 2024-10-24 17:32:08 +03:00
d678a639b8
Merge branch 'master' into api-context 2024-10-24 17:07:11 +03:00
453fea569a Merge pull request 'api-structs' (#117) from api-structs into master
Reviewed-on: urdt/ussd#117
2024-10-24 15:53:46 +02:00
5c75e35fe0 Delete coverage.html
delete cover.html
2024-10-24 15:45:52 +02:00
cff50538fa Delete cover.out
delete cover.out
2024-10-24 15:45:29 +02:00
69a4530269 Delete services/registration/locale/swa/default.mo
remove dev file
2024-10-24 15:41:47 +02:00
db19e38717
Merge remote-tracking branch 'refs/remotes/origin/api-structs' into api-structs 2024-10-24 16:37:07 +03:00
c796bbdcfc
correct create endpoint 2024-10-24 16:36:09 +03:00
2b34a0900c
check for status code and unmarshal on errResponse 2024-10-24 16:35:53 +03:00
e15bac98a5 Merge branch 'master' into menu-voucherlist 2024-10-24 16:31:49 +03:00
ee9a683eb0
Merge branch 'master' into menu-voucherlist 2024-10-24 16:30:44 +03:00
9274e585bd
Merge branch 'master' into menu-voucherlist 2024-10-24 16:26:32 +03:00
57a49819f4
Merge branch 'master' into api-structs 2024-10-24 16:22:41 +03:00
abc01b7cee
change to local setup endpoint 2024-10-24 16:21:34 +03:00
d19c20a9d7 Merge branch 'master' into api-structs 2024-10-24 15:19:06 +02:00
0c6144d262 Merge pull request 'send-menu-update' (#131) from send-menu-update into master
Reviewed-on: urdt/ussd#131
2024-10-24 15:15:11 +02:00
ec4e44a27c Merge branch 'master' into send-menu-update 2024-10-24 15:58:59 +03:00
69eb57f794 Merge branch 'master' into api-context 2024-10-24 14:51:25 +02:00
2347d64acc Merge pull request 'check-balance-update' (#132) from check-balance-update into master
Reviewed-on: urdt/ussd#132
2024-10-24 14:50:59 +02:00
39c0560abe
Updated the test 2024-10-24 15:21:48 +03:00
75459f852b
Return the full balance string 2024-10-24 15:12:57 +03:00
6200728435
Updated the menuhander test 2024-10-24 14:45:15 +03:00
579b46db65
Replace the public key with the sessionId 2024-10-24 14:34:12 +03:00
f99486c190
correct import 2024-10-24 12:07:00 +03:00
57a07af8ca
correct import 2024-10-24 12:06:44 +03:00
5692440099
move to testutil 2024-10-24 12:05:27 +03:00
651969668f
move to testutil 2024-10-24 12:05:11 +03:00
f3a028f1fc
move to testutil 2024-10-24 12:03:32 +03:00
9f2d57ea03
update tests 2024-10-24 10:10:14 +03:00
d74a4cc33b
update service mock method signatures 2024-10-24 10:10:03 +03:00
308ca99fb0
remove reload account creation 2024-10-24 10:02:32 +03:00
08e709f1b3
check for error responses 2024-10-24 10:02:15 +03:00
9bc9d04a49
use errresponse and okresponse for deserialization 2024-10-24 10:00:38 +03:00
a553731f02
Cleaned up code 2024-10-23 17:45:41 +03:00
fc0043e3f6
Adde the transactions node 2024-10-23 14:52:15 +03:00
d41ba79ae4
Adde the check_statement node 2024-10-23 14:51:59 +03:00
f36847d966
Added a placeholder function to get transactions 2024-10-23 14:51:17 +03:00
4011597d9c
Check specific db error 2024-10-23 14:02:13 +03:00
176473aa26
Rename prefix to vouchers 2024-10-23 13:54:42 +03:00
b41e52af63
pass context.Context 2024-10-23 12:45:54 +03:00
fb32dde136
run go mod tidy 2024-10-23 12:45:10 +03:00
1e6cf6a33a
run mod tidy 2024-10-23 11:08:51 +03:00
2725323f16
Merge branch 'master' into tests-refactor 2024-10-23 11:06:10 +03:00
5f1ee396d8
Fix PIN being requested twice 2024-10-23 06:35:19 +03:00
5f2c6cce16
add required track endpoint 2024-10-22 21:36:28 +03:00
3179ec1f62
add local track endpoint 2024-10-22 21:35:52 +03:00
b9a63f3c6f
merge dep 2024-10-22 21:30:48 +03:00
1d255372b2
Merge branch 'master' into api-structs 2024-10-22 21:05:51 +03:00
306666a15e
load and reload after halt 2024-10-22 20:37:30 +03:00
e05dbb4885
check for back option 2024-10-22 20:36:58 +03:00
637e107525
Merge branch 'master' into menu-voucherlist 2024-10-22 17:10:51 +03:00
59d0446020 Merge pull request 'postgres-switch' (#113) from postgres-switch into master
Reviewed-on: urdt/ussd#113
2024-10-22 16:04:56 +02:00
f37ec13c75
polish code 2024-10-22 16:31:29 +03:00
0547bc7e5f
added send menu test with dynamic max_amount 2024-10-22 14:24:22 +03:00
02cb75f97a
increase the size to resolve sink error 2024-10-21 17:14:59 +03:00
9c75942b0b
chore: remove commented code 2024-10-21 16:54:16 +03:00
5909659fa9
Use dynamic balance 2024-10-21 16:52:07 +03:00
eaac771722
move into testtag package 2024-10-21 16:48:24 +03:00
f3a5178de7
update imports 2024-10-21 16:47:43 +03:00
549d09890b
update imports 2024-10-21 16:47:25 +03:00
4a9ef6b5f2
move test account service to testutil 2024-10-21 16:47:00 +03:00
961d8d1a5c
update package import 2024-10-21 16:46:29 +03:00
a904cdbf44
move driver to testutil 2024-10-21 16:45:06 +03:00
3af943f77c
move account service tags switch to test tags package 2024-10-21 16:44:02 +03:00
14455f65cb
move account service to testutil 2024-10-21 16:43:24 +03:00
0c08654df3
move driver to testutil 2024-10-21 16:42:57 +03:00
acd0af25c6
catch api call error 2024-10-21 11:11:04 +03:00
66d2e2e838
add custodial api structs 2024-10-21 11:10:42 +03:00
4beeb9986a
use importable api structs 2024-10-21 11:10:23 +03:00
d81bc0eefb
use importable api structs 2024-10-21 11:10:01 +03:00
5b0a383513
use importable api structs 2024-10-21 11:09:37 +03:00
367d3f0593
remove manually added api.go file 2024-10-21 11:07:32 +03:00
415c807464
include the Database in context 2024-10-21 09:22:07 +03:00
9f562fe53e
use postgres directly from go-vise 2024-10-19 23:06:58 +03:00
3bf2045f15
added FetchVouchers to the TestAccountService 2024-10-19 16:07:40 +03:00
aced3e4fc3 Merge branch 'master' into menu-voucherlist 2024-10-19 15:38:54 +03:00
fb0d2db156 Merge branch 'master' into postgres-switch 2024-10-19 15:28:59 +03:00
a40fc37da4
implement postgres for the state store 2024-10-19 15:27:23 +03:00
f13f5996c1
remove thread abstraction from postgres 2024-10-19 14:51:41 +03:00
00a2beae50
rename file 2024-10-19 13:41:19 +03:00
25bc7006a4
show a balance of 0 and prevent sending when no voucher exists 2024-10-18 18:31:40 +03:00
f643aa4d14
update tests 2024-10-18 17:37:04 +03:00
b8860478b6
implement expected structs 2024-10-18 17:36:51 +03:00
847b91ca9e
Merge branch 'menu-api-errors' into api-structs 2024-10-18 17:15:05 +03:00
353e24de33
define api structs 2024-10-18 17:04:43 +03:00
1c57c95d93
use api structs 2024-10-18 17:04:02 +03:00
128a354b34
use api structs 2024-10-18 17:03:48 +03:00
81c4189c8e
update tests 2024-10-18 17:02:08 +03:00
b8e12e5215
update api endpoints 2024-10-18 17:01:21 +03:00
113f1a5b34 Merge pull request 'menu-traversal-v2' (#115) from menu-traversal-v2 into master
Reviewed-on: urdt/ussd#115
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2024-10-18 15:38:56 +02:00
4f04362835
pass error description to error response 2024-10-17 16:08:18 +03:00
fd8bfae8c7
updated the vise version to include the updated column 2024-10-17 15:35:35 +03:00
eea3be3a39
resolve failing test 2024-10-17 13:49:56 +03:00
849a950fbc Merge branch 'master' into menu-voucherlist 2024-10-17 13:44:31 +03:00
6727bd3769
polished code 2024-10-17 12:55:47 +03:00
9f8fcf1ed0
attach account service to handler 2024-10-17 12:54:11 +03:00
4a599b902d
define transaction 2024-10-17 12:49:51 +03:00
a759f47c8e Merge branch 'master' into postgres-switch 2024-10-17 12:49:28 +03:00
d181c34946
update handler and move transaction struct to models 2024-10-17 12:49:28 +03:00
4968cdff37
switch to postgres once the flag is set 2024-10-17 12:47:57 +03:00
bfa6eac4c2
define a test account service 2024-10-17 12:47:44 +03:00
1aeb18379c
added a db flag and Database to the context 2024-10-17 12:46:20 +03:00
667a21d950
pass account service as a param 2024-10-17 12:37:15 +03:00
4416c008fc
add menu traversal tests 2024-10-17 12:36:24 +03:00
0a7389a71d
explicitly reset authorize flag 2024-10-17 12:36:02 +03:00
383e64776d
chore: change pin to PIN 2024-10-17 12:35:44 +03:00
a27c1790b8
setup test data file 2024-10-17 12:34:17 +03:00
f81e3508ca
define engine to run tests 2024-10-17 12:33:38 +03:00
127219f510
define build for running online and offline tests 2024-10-17 12:33:09 +03:00
54cc33c819
Delete connstr in threadgdbm global channel map on close 2024-10-17 12:32:31 +03:00
a51f739d06
pass account service as a param 2024-10-17 12:31:33 +03:00
8d047ebe05
define universal group driver 2024-10-17 12:30:58 +03:00
4e840ac17c
add uuid 2024-10-17 12:30:36 +03:00
f73b7a8b04
setup api responses 2024-10-16 22:40:40 +03:00
e986eaa538 Merge pull request 'menu-api-errors' (#112) from menu-api-errors into master
Reviewed-on: urdt/ussd#112
2024-10-16 19:08:46 +02:00
d8db8df643
use go-vise v0.2.0 2024-10-15 23:42:39 +03:00
09eac03e10
use env variables 2024-10-15 23:41:16 +03:00
51122d0fc5
added an env.example file 2024-10-15 22:31:37 +03:00
d05c666513 Merge branch 'master' into menu-voucherlist 2024-10-15 17:08:48 +03:00
a336856c9b
use separate functions to process voucher data 2024-10-15 17:02:51 +03:00
0be570ae2d
add check for api call failure 2024-10-15 16:31:31 +03:00
6a36bc43b5
add check for api call failure 2024-10-15 16:31:15 +03:00
1d27a88908
add test on validate amount 2024-10-15 16:30:29 +03:00
f378f15422
updated tests 2024-10-15 16:29:51 +03:00
b2fb9faf6c
use the active balance to validate the amount 2024-10-15 16:17:33 +03:00
859e203a00
removed debug comments 2024-10-15 15:54:43 +03:00
6c6af5ec21
set a default voucher as the active sym if none exists 2024-10-15 15:46:02 +03:00
8ed98b3e6c
resolve case issue 2024-10-15 14:53:00 +03:00
4889e6d18b
Merge remote-tracking branch 'origin' into menu-api-errors 2024-10-15 14:04:45 +03:00
368c25125a
set flag count to 128 2024-10-15 13:59:49 +03:00
283793a2ae
add swahili menu option 2024-10-15 13:57:45 +03:00
bec7e5c69f
update: fetch balances in a sepate function,show profile information in swahili and english 2024-10-15 13:57:05 +03:00
d638aba85e
update tests 2024-10-15 13:50:28 +03:00
df7788dd0b
return actual reponses on the api calls 2024-10-15 13:48:14 +03:00
4a62773098
add handler fetching custodial balances 2024-10-15 13:44:50 +03:00
26d315b032
add check for api call failure 2024-10-15 13:42:20 +03:00
1927544533
reset authorized flag 2024-10-15 13:40:40 +03:00
c641a0c669
add api failure nodes 2024-10-14 23:19:09 +03:00
952da86931
update balance nodes 2024-10-14 23:18:42 +03:00
be6391686f
update return type 2024-10-14 23:17:57 +03:00
65794c1b20
add api calls flag 2024-10-14 23:17:17 +03:00
lash
967e53d83b Merge branch 'master' into lash/ssh-4 2024-10-14 14:50:12 +01:00
b058f9d770 Merge pull request 'Adapter to enable subdomain of db key prefixes' (#102) from lash/subprefix into master
Reviewed-on: urdt/ussd#102
2024-10-14 15:11:07 +02:00
7df77a1343
updated the ValidateAmount to also check the active symbol, updated tests 2024-10-12 20:07:06 +03:00
f5dbfe553d
use the check_balance for the max_amount 2024-10-12 20:06:00 +03:00
7fe8f0b7d5
updated the args under FetchVouchers 2024-10-12 18:03:13 +03:00
a9f9867976
added the TestSetVoucher 2024-10-12 17:36:00 +03:00
b6d24bf929
update the TestCheckBalance 2024-10-12 16:29:12 +03:00
e9684fcf45
check whether the active symbol is empty 2024-10-12 16:28:02 +03:00
a5b1c5b74e
cleaned up the code 2024-10-12 14:32:40 +03:00
672eebb8fb
display the balance based on the symbol 2024-10-11 09:42:08 +03:00
8f834b3d76
ensure that a user is authorized 2024-10-11 09:41:47 +03:00
6c93fb76b1
correctly added the flag and the flag count 2024-10-11 09:36:43 +03:00
ea2df55295
use go-vise v0.2.0 2024-10-10 15:18:13 +03:00
7c08a0f0af
add temp and active balance 2024-10-10 14:48:23 +03:00
9ad7d5a522
set the active symbol 2024-10-09 15:39:06 +03:00
6c904a8b3f
add the temporary and active symbol 2024-10-09 15:38:19 +03:00
9ccb6cc066
use 99 as the quit 2024-10-09 15:05:59 +03:00
2c98a8e133
read token list from json file 2024-10-08 14:34:21 +03:00
4b6fd35e7a
define importable voucher response 2024-10-08 13:43:57 +03:00
b3c7a3a337
Merge remote-tracking branch 'refs/remotes/origin/menu-voucherlist' into menu-voucherlist 2024-10-08 13:43:19 +03:00
7b374ad801
define importable token list 2024-10-08 13:41:09 +03:00
cb4a52e4f2
view a selected voucher and verify the PIN 2024-10-07 16:16:57 +03:00
06ebcc0f07
added swahili template 2024-10-07 16:15:13 +03:00
e4ed9a65bb
store the symbols and balances 2024-10-07 13:49:12 +03:00
755899be4e
store the pre-rendered vouchers list 2024-10-07 08:59:15 +03:00
4dede757d2 Merge branch 'lash/subprefix' into menu-voucherlist 2024-10-07 08:06:37 +03:00
517f980664
get the vouchers list and store in gdbm 2024-10-05 16:56:49 +03:00
31aea6b807
added model and func to fetch vouchers from the API 2024-09-28 14:07:37 +03:00
3a46fda769
use save_temporary_pin and updated tests 2024-09-28 12:26:37 +03:00
c7bdfe90b7 Merge branch 'master' into menu-voucherlist 2024-09-28 11:07:36 +03:00
lash
d246cdee51
Rename datatype const name for ssh prefix 2024-09-27 21:25:21 +01:00
lash
d518a76536 Merge branch 'lash/subprefix' into lash/ssh-4 2024-09-27 21:18:25 +01:00
lash
2a93ea7a0c
Remove out-of-context extend key 2024-09-27 21:16:08 +01:00
lash
f89b1acc6c Merge branch 'master' into lash/subprefix 2024-09-27 21:15:17 +01:00
ddeafe015b Merge pull request 'tests-update' (#100) from tests-update into master
Reviewed-on: urdt/ussd#100
2024-09-27 22:14:50 +02:00
lash
1dc8b054eb
Add sub-prefix db wrapper 2024-09-27 21:10:03 +01:00
60134f14e9 Merge branch 'master' into menu-voucherlist 2024-09-27 19:11:35 +03:00
4c33945081
use latest go-vise update 2024-09-27 19:10:08 +03:00
a3ff3be5b1
clean up 2024-09-27 16:32:47 +03:00
ea52a7cf0a
update tests 2024-09-26 23:11:37 +03:00
a993026380
update tests 2024-09-26 23:07:48 +03:00
lash
6f65c33be4
Re-add ssh 2024-09-26 15:15:06 +01:00
lash
4ee241714b
Attempt 2 revert changes from ssh 2024-09-26 15:08:15 +01:00
lash
d7dc743fa2 Merge remote-tracking branch 'origin/master' 2024-09-26 15:07:13 +01:00
lash
c220cbb767
Revert accidental merge of ssh 2024-09-26 15:05:17 +01:00
0dc322729f Merge pull request 'SSH server entry point.' (#77) from lash/ssh-2 into master
Reviewed-on: urdt/ussd#77
2024-09-26 15:55:51 +02:00
726d6dd338 Merge pull request 'menu-profile-edit' (#82) from menu-profile-edit into master
Reviewed-on: urdt/ussd#82
2024-09-26 15:48:55 +02:00
a8b202bd79 Merge branch 'master' into menu-profile-edit 2024-09-25 15:19:04 +02:00
221db4e998
return a numbered list of vouchers 2024-09-25 16:06:06 +03:00
0e376e0d9e
include back and quit 2024-09-25 16:03:08 +03:00
7aa44caea2
add voucher nodes 2024-09-25 15:57:23 +03:00
188cb573dd
add dummy vouchers list 2024-09-25 13:27:13 +03:00
6dbd250694
remove extra spaces 2024-09-25 09:29:26 +03:00
cc760e7698
remove move 2024-09-25 09:20:45 +03:00
8648ea599c
add catch node 2024-09-25 09:20:45 +03:00
77e4c5d43a
reset the positon of LOAD function 2024-09-25 09:20:44 +03:00
b15ba367c4
change position of LOAD function 2024-09-25 09:20:44 +03:00
4db862bc97
LOAD and RELOAD get_amount 2024-09-25 09:20:43 +03:00
6ad67f6adc
change position of LOAD 2024-09-25 09:20:42 +03:00
0caf82a27e Merge pull request 'fix-repeated-nodes' (#81) from fix-repeated-nodes into master
Reviewed-on: urdt/ussd#81
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2024-09-25 01:48:34 +02:00
a430857309 Merge branch 'master' into fix-repeated-nodes 2024-09-25 01:41:43 +02:00
2643c0c9ff
only have a -d for the engineDebug 2024-09-24 16:11:22 +03:00
b8852e1ab3
add engineDebug and stateDebug flags 2024-09-24 14:10:10 +03:00
0dea34daab
resolve confilict 2024-09-24 09:18:21 +03:00
8057313c78
Merge remote-tracking branch 'remotes/origin/master' into menu-profile-edit 2024-09-24 09:10:17 +03:00
1bd96d0689
setup dedicated nodes for case selection 2024-09-24 09:02:04 +03:00
bbfe46f162
use current rendering symbol for case selection 2024-09-24 09:01:19 +03:00
eff2cbde8b
setup check for unused code 2024-09-24 09:00:31 +03:00
5c85ecffd1
remove unused code 2024-09-24 09:00:13 +03:00
lash
ad1f9233ca Merge branch 'master' into lash/ssh-2 2024-09-23 20:26:47 +01:00
e9fdd1ddbe Merge pull request 'Threaded gdbm' (#76) from lash/thread-gdbm into master
Reviewed-on: urdt/ussd#76
2024-09-23 21:25:37 +02:00
8a03b05c90
reset the positon of LOAD function 2024-09-23 21:20:57 +03:00
lash
c18c40b1b8 Merge branch 'lash/thread-gdbm' into lash/ssh-2 2024-09-23 18:56:38 +01:00
5a38b40eaf Merge branch 'lash/thread-gdbm' into fix-repeated-nodes 2024-09-23 20:55:56 +03:00
lash
6112ca175f Merge branch 'master' into lash/thread-gdbm 2024-09-23 18:54:18 +01:00
c7ebca4729
update template text 2024-09-23 20:20:41 +03:00
fa0070b9a8
add swahili templates 2024-09-23 20:20:20 +03:00
4a447fbb45
update profile update 2024-09-23 20:10:37 +03:00
cb32cfe9d8
update dep 2024-09-23 20:09:51 +03:00
cf4e80dcb8
update profile edit nodes 2024-09-23 20:09:37 +03:00
lash
c02d70eaa4
Upgrade dep, improve logging 2024-09-23 17:35:17 +01:00
909d1f3409
change position of LOAD function 2024-09-23 14:16:01 +03:00
66cf90f044
LOAD and RELOAD get_amount 2024-09-23 14:13:26 +03:00
74d5da3987 Merge branch 'lash/thread-gdbm' into fix-repeated-nodes 2024-09-23 11:40:29 +03:00
f215159725
change position of LOAD 2024-09-23 11:38:07 +03:00
a6301163eb
use latest commit from go-vise 0.2.0 2024-09-23 09:59:21 +03:00
lash
a07fce527f Merge branch 'lash/thread-gdbm' into lash/ssh-2 2024-09-22 16:26:59 +01:00
lash
8a5209584d
Update go module deps 2024-09-22 16:25:04 +01:00
lash
ddc8f6dad1
Update module dep 2024-09-22 16:24:09 +01:00
lash
c2b68231f5
Update gitignore 2024-09-22 16:15:40 +01:00
lash
3f3dbf414c
Clarify keyfile use in readme 2024-09-22 16:13:30 +01:00
lash
e4c3e9f015
Add ssh instructions, log host key 2024-09-22 16:09:57 +01:00
lash
9b71244391 Merge branch 'lash/thread-gdbm' into lash/ssh-2 2024-09-22 15:43:18 +01:00
lash
ada1f26b68
Add keystore class, separate keystore tool executable 2024-09-22 15:41:55 +01:00
lash
935b777e57
Factor out ssh service code 2024-09-22 14:41:01 +01:00
lash
7d3ff690f0
Remove useless 'registered' member in thread gdbm 2024-09-22 03:10:58 +01:00
lash
a455cfb854
Return if duplicate connect 2024-09-22 03:09:53 +01:00
lash
19372c17f4
Reinstate ssh executable 2024-09-22 03:06:24 +01:00
lash
1cc2f58ab3
Remove ssh 2024-09-22 03:03:03 +01:00
lash
3756bdc98a Merge remote-tracking branch 'origin/lash/ssh' into lash/ssh 2024-09-22 02:58:18 +01:00
lash
e07f88b368
Settable ssh keyfile, host, port 2024-09-22 02:57:10 +01:00
472624a831 Merge branch 'master' into lash/ssh 2024-09-22 03:38:53 +02:00
lash
84422684c5
Rehabilitate all executables 2024-09-22 02:33:11 +01:00
lash
28fc7a0462
Implement threaded gdbm in storageservice 2024-09-22 02:28:00 +01:00
lash
78d349ccc7
Add threaded gdbm wrapper 2024-09-22 02:21:56 +01:00
lash
0813a619b4
Add hacky db closer function in ssh 2024-09-21 21:32:02 +01:00
lash
5ed9d2643b
WIP can execute single session, but persister fails in next 2024-09-21 18:56:20 +01:00
lash
8dcba67fe9
WIP can execute single session, but persister fails in next 2024-09-21 18:49:11 +01:00
lash
5cac17676a
WIP adapt ssh server sketch to urdt setup 2024-09-21 00:32:39 +01:00
4439cc249a Merge pull request 'go-vise-0.2.0' (#71) from go-vise-0.2.0 into master
Reviewed-on: urdt/ussd#71
2024-09-21 00:06:07 +02:00
e754773bce
remove need for initial Exec before loop 2024-09-20 22:16:43 +03:00
63c7c65a00
rename all WriteResult to Flush 2024-09-20 22:15:24 +03:00
9925b3a2e5
use updated latest commit from go-vise 0.2.0 2024-09-20 22:12:52 +03:00
a1056cf287
removed unused code 2024-09-20 13:54:23 +03:00
e6e701a609
remove init and use Exec 2024-09-20 13:13:20 +03:00
b66891a646
use latest commit from go-vise 0.2.0 2024-09-20 13:10:44 +03:00
7197382911 Merge pull request 'Code refactor' (#66) from wip-main-refactor into master
Reviewed-on: urdt/ussd#66
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2024-09-19 20:19:16 +02:00
5c5f4cbc8e Merge branch 'master' into wip-main-refactor 2024-09-19 20:19:06 +02:00
e581a1ad2f
factor out getflag 2024-09-19 21:04:09 +03:00
929e812992 Merge pull request 'at-return-output' (#63) from at-return-output into master
Reviewed-on: urdt/ussd#63
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2024-09-19 18:23:13 +02:00
3fe66466c5
renamed test file and added server.go tests 2024-09-19 18:52:13 +03:00
f6979868e5
added at_session_handler tests 2024-09-19 17:19:09 +03:00
e8be64ae28
added http related mocks 2024-09-19 17:18:14 +03:00
e4d8bfad7b
moved the mocks package 2024-09-19 17:17:28 +03:00
96358959b4
remove unused code 2024-09-19 17:04:08 +03:00
bc9dfe4f65
remove redundant code 2024-09-19 17:01:23 +03:00
ffa00ae15c
refactor code 2024-09-19 16:18:21 +03:00
13294b42d3
refactor code 2024-09-19 16:16:17 +03:00
81159e77d1
refactor code 2024-09-19 16:15:29 +03:00
5bd51b280e
add storage service for menu 2024-09-19 15:57:11 +03:00
71e1ae6e3c
add function registration service 2024-09-19 15:54:23 +03:00
10de039da0
remove obsolete code 2024-09-18 15:42:56 +03:00
27aa71e0ee
only set the code to 200 if no error exists 2024-09-18 15:11:49 +03:00
a9a429824c
return if the sessionId cannot be retrieved from the request 2024-09-18 14:52:56 +03:00
4098ac8a19 Merge pull request 'change-language' (#58) from change-language into master
Reviewed-on: urdt/ussd#58
2024-09-17 18:31:10 +02:00
2982f08b41 Merge branch 'master' into change-language 2024-09-17 18:30:52 +02:00
75ab9c66a3
run TestSetLanguage with execPath instead of input 2024-09-17 18:54:07 +03:00
95f02231b3 Merge pull request 'Unit tests' (#62) from wip-unit-tests into master
Reviewed-on: urdt/ussd#62
2024-09-17 15:55:33 +02:00
599f7a2857
add more tests 2024-09-17 15:44:22 +03:00
2e7c07e6f4
added missing functions to the other getHandlers 2024-09-17 15:31:44 +03:00
01f7571185
use dedicated nodes to set the language 2024-09-17 15:29:21 +03:00
065c8e5c1d
use a single set_language function for setting and changing language 2024-09-17 15:26:50 +03:00
dc14480519 remove extra space 2024-09-16 17:29:27 +03:00
aaf4923f64 ensure a PIN is set before changing the language 2024-09-16 17:29:27 +03:00
e9c645bd87 added the profile info on the swa menu template 2024-09-16 17:29:27 +03:00
1be6da9139 remove new lines on templates and menus to clean up the empty spaces on the menu 2024-09-16 17:29:27 +03:00
fa2930d93a added quit menu to handle eng and swa 2024-09-16 17:29:27 +03:00
a409e292ab add the change_language functionality to the account menu 2024-09-16 17:29:27 +03:00
00c86a2850 change language 2024-09-16 17:29:27 +03:00
4daac7e90b added change_language node and templates 2024-09-16 17:29:27 +03:00
06e23565df added the SetNewLanguage function 2024-09-16 17:29:27 +03:00
b19188165b Merge pull request 'wip-menu-help' (#56) from wip-menu-help into master
Reviewed-on: urdt/ussd#56
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2024-09-16 16:21:49 +02:00
2ed9f083bb add quit with helpline info
add quit with helpline info
2024-09-16 15:17:56 +01:00
e323ffa078 Merge pull request 'Pin reset' (#59) from wip-pin-reset into master
Reviewed-on: urdt/ussd#59
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2024-09-16 16:14:52 +02:00
68de83af97 Merge pull request 'Allow setting go-vise path for asm executable in makefile' (#57) from lash/vise-make-var into master
Reviewed-on: urdt/ussd#57
2024-09-16 15:49:58 +02:00
a3f2b23128
add pin reset templates for swahili 2024-09-16 15:17:15 +03:00
09f970db9b
navigate to main menu after successful pin reset 2024-09-16 14:59:26 +03:00
04edd90c21
fix sink issue onback option 2024-09-16 14:58:56 +03:00
a3f410875a
define temporary key value 2024-09-16 14:39:42 +03:00
3f3e98e637
add pin reset handlers 2024-09-16 14:39:01 +03:00
660f8b7aa2
add pin reset nodes 2024-09-16 14:30:47 +03:00
lash
8ae3372c36
Allow setting go-vise path for asm executable in makefile 2024-09-14 21:34:11 +01:00
3a7c3ffc67 Merge pull request 'wip-unit-tests' (#55) from wip-unit-tests into master
Reviewed-on: urdt/ussd#55
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2024-09-14 22:29:52 +02:00
78c033e61c
remove deprecated code 2024-09-14 20:59:08 +03:00
b5ef483f34
clean up tests 2024-09-14 20:07:17 +03:00
006eef0a28
add testdata loader 2024-09-14 20:02:21 +03:00
e99a788c60
add tests 2024-09-14 20:01:58 +03:00
b5d33a98f0 Merge pull request 'Enable CLI driver of async session' (#49) from lash/async-driver into master
Reviewed-on: urdt/ussd#49
2024-09-14 16:52:06 +02:00
f4f475bd45 Merge pull request 'africas-talking' (#50) from africas-talking into lash/async-driver
Reviewed-on: urdt/ussd#50
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2024-09-14 16:28:05 +02:00
6fe2e7287f Update the func name to Output
Signed-off-by: Alfred Kamanda <alfredkamandamw@gmail.com>
2024-09-14 16:01:18 +02:00
1e9c9cf6ad
removed AT specific code 2024-09-14 15:57:16 +03:00
3cb0b099e4
use the new AtSessionHandler 2024-09-14 15:55:45 +03:00
b53658e038
have AtOutput as an option 2024-09-13 16:03:31 +03:00
512460fdeb
Added Custom AtOutput to append CON or END to output 2024-09-13 16:02:04 +03:00
762f90adf6
Added Continue bool to track whether the execution should be terminated 2024-09-12 23:52:35 +03:00
lash
9b4a4eeaf4
Temporary solution for make sure storage object gets put back in all cases of execution 2024-09-12 16:46:11 +01:00
5e4e6a21a0
Added africastalking binary 2024-09-12 15:56:57 +03:00
ffeb28e851
Use latest go-vise package 2024-09-12 15:56:34 +03:00
lash
9c751aff30
Update go-vise 2024-09-12 04:19:13 +01:00
lash
b31d3b907a
Add shutdown to async, rehabilitate http cmd 2024-09-12 04:13:57 +01:00
lash
d49f866ca4
Factor out methods common to http and async cli 2024-09-12 04:07:55 +01:00
lash
dde9f552a6
Isolate http specific parts to minimal 2024-09-12 03:30:23 +01:00
0f9b5551ec Merge pull request 'Implement http server for the URDT vise engine' (#41) from lash/http-server into master
Reviewed-on: urdt/ussd#41
2024-09-12 00:13:14 +02:00
lash
514e043e38
Fix symptom of handler missing persister 2024-09-11 17:53:12 +01:00
lash
836e5fe8ee
Revert africas talking changes in http 2024-09-11 17:32:55 +01:00
lash
660fcaa0b6 Import go-vise fixing missing exit on state reset 2024-09-11 17:25:56 +01:00
44015b1c76
Parse the request body to get the PhoneNumber and Input text 2024-09-11 15:40:49 +03:00
lash
7438531900
Update govise to include removed dead asm code 2024-09-11 04:10:05 +01:00
lash
681f293d3c
Externalize requestparser, flush persister on http request end 2024-09-10 23:09:10 +01:00
lash
8e3ff27bb8
Ensure db close on http signal shutdown, correct stores to provider 2024-09-10 20:44:10 +01:00
lash
dd2468a4d7 Http server harness
Add storage retrieval solution for http handler

Successfully executed account regisration using http

Set upstream go-vise dependency version in go.mod

Adapt menuhandler to upstream
2024-09-10 13:59:36 +01:00
63cee42261 Merge pull request 'wip-code-check' (#44) from wip-code-check into master
Reviewed-on: urdt/ussd#44
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2024-09-10 14:25:50 +02:00
9f034967b5
remove resource directory 2024-09-10 12:32:19 +03:00
ad48890a9f
remove deprecated code 2024-09-10 11:24:09 +03:00
c0a3ad7e2b
delete deprecated code 2024-09-10 11:23:41 +03:00
a3dffdf4e9
match code refactor 2024-09-10 11:23:25 +03:00
47d39a1c6f
remove commented test 2024-09-09 17:24:43 +03:00
f5f1cbaaba
cleanup 2024-09-09 17:18:07 +03:00
134aa96194
implement db for user datastore 2024-09-09 17:16:08 +03:00
0cdb23fbea
setupmock for user datastore 2024-09-09 17:15:35 +03:00
ca655b0cdc
add tests 2024-09-09 17:15:04 +03:00
da93444d3f
remove deprecated code 2024-09-09 10:14:40 +03:00
c2564a9b8f
remove go-vise subdirectory 2024-09-09 10:12:29 +03:00
33c6b35f8f
Merge branch 'origin/master' into wip-code-check 2024-09-09 09:56:00 +03:00
ba72b3bf44
Merge branch 'master' into wip-code-check 2024-09-09 09:45:29 +03:00
e961b6cb6a
Merge branch 'wip-code-check' 2024-09-09 09:22:08 +03:00
2c059afa7d
resolve 2024-09-07 22:05:09 +03:00
9aab7d3a9b
Merge branch 'master' into wip-code-check 2024-09-07 22:04:30 +03:00
a25beb5b80
Merge branch 'wip-code-check' 2024-09-07 21:54:00 +03:00
39d27209cd
Merge remote-tracking branch 'refs/remotes/origin/wip-code-check' into wip-code-check 2024-09-07 18:10:40 +03:00
16a56ef29d
add go-vise 2024-09-07 18:09:55 +03:00
6d02ea79ec
add go-vise 2024-09-07 18:09:13 +03:00
deb4706b1d
Test commit 2024-09-07 17:51:30 +03:00
e14fd5e496
Return the response and the error 2024-09-07 17:41:05 +03:00
01c13ec581
make packKey accessible from tests 2024-09-07 16:25:29 +03:00
dd97531861
remove uimplemented tests 2024-09-07 16:24:37 +03:00
be33b7458f
cleanup code 2024-09-07 16:22:08 +03:00
4c3f63a48f
create an account only if not found in gdbm 2024-09-07 10:36:00 +03:00
d1d5c897d1
refactor 2024-09-07 09:55:59 +03:00
04ea11dd6d
setup db mock 2024-09-07 09:55:47 +03:00
5722552395
remove old mocks 2024-09-07 09:55:13 +03:00
421fbe5543
setup mock for the acccount service 2024-09-07 09:55:00 +03:00
de24ca0648
Mock the gdm nd updated the TestSaveFirstname and TestSaveFamilyname 2024-09-07 09:30:20 +03:00
175cbd1983
setup template test 2024-09-06 17:51:07 +03:00
8175d6ac12
setup db mock 2024-09-06 17:50:33 +03:00
d4bae50ff0
Merge remote-tracking branch 'refs/remotes/origin/wip-code-check' into wip-code-check 2024-09-06 16:54:41 +03:00
d7376a4196
format error 2024-09-06 16:53:22 +03:00
eb9f470ac5
Update the GetProfileInfo to get data from gdbm 2024-09-06 16:17:26 +03:00
7a12588744
remove deprecated code 2024-09-06 12:42:24 +03:00
6947b1e4a4
rename getflags to getparser 2024-09-06 11:03:01 +03:00
2cc85379cc
update log 2024-09-06 11:02:33 +03:00
d001c5a7fc
Write and read data from gdbm 2024-09-06 09:33:39 +03:00
de8c7ce34a
Added user data to db.go util 2024-09-06 08:35:01 +03:00
lash
cad8e86c8b
Remove manual init calls in handler funcs 2024-09-05 23:55:54 +01:00
lash
0feb013c78
Ensure handler init when state and cache is available 2024-09-05 20:40:40 +01:00
643b4d87a9
read account pin of gdbm store 2024-09-05 20:30:28 +03:00
5abaf28f49
remove explicit attachment of state to engine 2024-09-05 20:26:52 +03:00
17804e7641
Save the actual PIN and verify it 2024-09-05 19:50:02 +03:00
lash
db3ec1991d
Remove obsolete store and persister global 2024-09-05 16:45:35 +01:00
lash
62b7adb967
Fix missing byte allocation for typ serialize 2024-09-05 15:41:27 +01:00
lash
6fa5f49bc0
Remove impossible nil check in handler 2024-09-05 15:28:53 +01:00
2bf7a5c246
setup db keys 2024-09-05 17:12:38 +03:00
98c74dffc4
use state from persister 2024-09-05 17:09:30 +03:00
771a1e8169
code refactoring 2024-09-05 17:07:20 +03:00
220c5b2081
remove commented code 2024-09-04 20:22:25 +03:00
2fc8a0e5a7
use fsDb for the resources 2024-09-04 19:57:08 +03:00
c6c66f956a Merge pull request 'wip-flag-migration' (#28) from wip-flag-migration into master
Reviewed-on: urdt/ussd#28
2024-09-04 11:25:33 +02:00
1957606bc2
Added log to show debug the flag loaded 2024-09-04 12:19:34 +03:00
8ffc5d67cc
Removed mutex 2024-09-04 12:01:51 +03:00
2d7b6bd125
Removed unused code 2024-09-03 22:28:48 +03:00
5105e902f1
Process flags once and make them available across functions 2024-09-03 19:06:37 +03:00
19b2fa65fa
Merge remote-tracking branch 'refs/remotes/origin/wip-flag-migration' into wip-flag-migration 2024-09-03 18:00:06 +03:00
ee4db50e00
remove unused code 2024-09-03 17:59:03 +03:00
99d18322b2
Append to the correct flag set/reset 2024-09-03 15:34:19 +03:00
a07a8703f4
remove flag setting invalid pin entry 2024-09-03 15:13:55 +03:00
94f12edeaf
Merge remote-tracking branch 'refs/remotes/origin/wip-flag-migration' into wip-flag-migration 2024-09-03 15:08:45 +03:00
fee51edade
append sessionid to the gdbm file 2024-09-03 15:07:49 +03:00
f90fde90fb
Register flags in debugger from the csv 2024-09-03 15:04:09 +03:00
ab6433168a
Resolve bug on transaction confirmation PIN 2024-09-03 15:02:31 +03:00
0c360c0cc4
remove panics after failed execution 2024-09-03 13:19:32 +03:00
560714838f
fix menu termination on invalid pin entry 2024-09-03 11:51:14 +03:00
c365eaa1d1
remove unused code 2024-09-02 21:24:16 +03:00
337419c9f2
Merge remote-tracking branch 'refs/remotes/origin/wip-flag-migration' into wip-flag-migration 2024-09-02 21:10:41 +03:00
d4c4db09f3
load profile data from gdbm 2024-09-02 21:09:39 +03:00
3a3ddc9922
Use FlagParser on main.go and delete the flags.go file 2024-09-02 21:06:42 +03:00
1c1ea74088
Merge remote-tracking branch 'refs/remotes/origin/wip-flag-migration' into wip-flag-migration 2024-09-02 17:12:01 +03:00
14c8230fd4
code cleanup 2024-09-02 17:11:08 +03:00
b6e4ba7ede
Verify PIN using the one in the db 2024-09-02 17:08:57 +03:00
2b511aba4c
remove commented code 2024-09-02 16:39:04 +03:00
626fca1a55
Merge remote-tracking branch 'refs/remotes/origin/wip-flag-migration' into wip-flag-migration 2024-09-02 16:30:58 +03:00
0c96831378
use gdbm 2024-09-02 16:05:13 +03:00
fe4df78f80
use gdbm for user info storage 2024-09-02 16:04:53 +03:00
31be1fa221
Use flags from pp.csv on the menuhandler functions and tests 2024-09-02 14:00:02 +03:00
ba4d0abcda
improve doc line 2024-09-02 10:03:57 +03:00
632dd860ff
Use flags from pp.csv on the Authorize function 2024-08-31 17:16:57 +03:00
07c8638a6d
use correct symbol name 2024-08-31 15:09:34 +03:00
c71f6e76d7
Merge remote-tracking branch 'refs/remotes/origin/wip-flag-migration' into wip-flag-migration 2024-08-31 14:56:18 +03:00
2559b4e604
add test profile 2024-08-31 14:55:54 +03:00
460e6fa2c8
Renamed duplicate flag 2024-08-31 14:50:45 +03:00
c3c5c83662
Change the order of flags 2024-08-31 14:48:02 +03:00
143c9b14a1
Renamed the flags 2024-08-31 12:58:48 +03:00
42ab2dd577
Use preprocessor flags 2024-08-31 12:16:36 +03:00
26959be149 Fixed bug on transaction pin node 2024-08-31 12:09:02 +03:00
118b5577bb
Merge remote-tracking branch 'refs/remotes/origin/wip-flag-migration' into wip-flag-migration 2024-08-31 12:06:42 +03:00
4e69fa454d
use string flags 2024-08-31 12:02:44 +03:00
9fb3ef8e2a
Use preprocessor flags 2024-08-31 11:56:36 +03:00
ec4201139a
add _flag suffix 2024-08-31 11:35:29 +03:00
bcc73dec23
Add the flag file during build 2024-08-31 11:27:47 +03:00
828f9a17fc Added the csv containing string flags 2024-08-31 10:30:10 +03:00
de4aaeb02b
use script dir for parser 2024-08-31 10:26:49 +03:00
cc323707fc
setup parser 2024-08-31 10:21:20 +03:00
ef0c207fc4 Merge pull request 'wip-account-creation' (#4) from wip-account-creation into master
Reviewed-on: urdt/ussd#4
Reviewed-by: lash <accounts-grassrootseconomics@holbrook.no>
2024-08-30 14:37:58 +02:00
205 changed files with 1605 additions and 2574 deletions

20
.env.example Normal file
View File

@ -0,0 +1,20 @@
#Serve Http
PORT=7123
HOST=127.0.0.1
#AfricasTalking USSD POST endpoint
AT_ENDPOINT=/ussd/africastalking
#PostgreSQL
DB_CONN=postgres://postgres:strongpass@localhost:5432/urdt_ussd
#DB_TIMEZONE=Africa/Nairobi
#DB_SCHEMA=vise
#External API Calls
CUSTODIAL_URL_BASE=http://localhost:5003
BEARER_TOKEN=eyJeSIsInRcCI6IkpXVCJ.yJwdWJsaWNLZXkiOiIwrrrrrr
DATA_URL_BASE=http://localhost:5006
#Language
DEFAULT_LANGUAGE=eng
LANGUAGES=eng, swa

3
.gitignore vendored
View File

@ -4,3 +4,6 @@ go.work*
**/*/*.bin
**/*/.state/
cmd/.state/
id_*
*.gdbm
*.log

View File

@ -1,9 +0,0 @@
# ussd
> USSD
USSD service.
## License
[AGPL-3.0](LICENSE).

View File

@ -1,146 +0,0 @@
package main
import (
"context"
"flag"
"fmt"
"os"
"path"
"git.defalsify.org/vise.git/cache"
"git.defalsify.org/vise.git/engine"
"git.defalsify.org/vise.git/persist"
"git.defalsify.org/vise.git/resource"
"git.defalsify.org/vise.git/state"
"git.grassecon.net/urdt/ussd/internal/handlers/ussd"
"git.grassecon.net/urdt/ussd/internal/models"
)
var (
scriptDir = path.Join("services", "registration")
)
func main() {
var dir string
var root string
var size uint
var sessionId string
flag.StringVar(&dir, "d", ".", "resource dir to read from")
flag.UintVar(&size, "s", 0, "max size of output")
flag.StringVar(&root, "root", "root", "entry point symbol")
flag.StringVar(&sessionId, "session-id", "default", "session id")
flag.Parse()
fmt.Fprintf(os.Stderr, "starting session at symbol '%s' using resource dir: %s\n", root, dir)
ctx := context.Background()
st := state.NewState(16)
st.UseDebug()
state.FlagDebugger.Register(models.USERFLAG_LANGUAGE_SET, "LANGUAGE_CHANGE")
state.FlagDebugger.Register(models.USERFLAG_ACCOUNT_CREATED, "ACCOUNT_CREATED")
state.FlagDebugger.Register(models.USERFLAG_ACCOUNT_SUCCESS, "ACCOUNT_SUCCESS")
state.FlagDebugger.Register(models.USERFLAG_ACCOUNT_PENDING, "ACCOUNT_PENDING")
state.FlagDebugger.Register(models.USERFLAG_INCORRECTPIN, "INCORRECTPIN")
state.FlagDebugger.Register(models.USERFLAG_INCORRECTDATEFORMAT, "INVALIDDATEFORMAT")
state.FlagDebugger.Register(models.USERFLAG_INVALID_RECIPIENT, "INVALIDRECIPIENT")
state.FlagDebugger.Register(models.USERFLAG_PINMISMATCH, "PINMISMATCH")
state.FlagDebugger.Register(models.USERFLAG_PIN_SET, "PIN_SET")
state.FlagDebugger.Register(models.USERFLAG_INVALID_RECIPIENT_WITH_INVITE, "INVALIDRECIPIENT_WITH_INVITE")
state.FlagDebugger.Register(models.USERFLAG_INVALID_AMOUNT, "INVALIDAMOUNT")
state.FlagDebugger.Register(models.USERFLAG_ALLOW_UPDATE, "UNLOCKFORUPDATE")
state.FlagDebugger.Register(models.USERFLAG_VALIDPIN, "VALIDPIN")
state.FlagDebugger.Register(models.USERFLAG_VALIDPIN, "ACCOUNTUNLOCKED")
state.FlagDebugger.Register(models.USERFLAG_ACCOUNT_CREATION_FAILED, "ACCOUNT_CREATION_FAILED")
state.FlagDebugger.Register(models.USERFLAG_SINGLE_EDIT, "SINGLEEDIT")
rfs := resource.NewFsResource(scriptDir)
ca := cache.NewCache()
cfg := engine.Config{
Root: "root",
SessionId: sessionId,
}
dp := path.Join(scriptDir, ".state")
err := os.MkdirAll(dp, 0700)
if err != nil {
fmt.Fprintf(os.Stderr, "state dir create exited with error: %v\n", err)
os.Exit(1)
}
pr := persist.NewFsPersister(dp)
en, err := engine.NewPersistedEngine(ctx, cfg, pr, rfs)
if err != nil {
pr = pr.WithContent(&st, ca)
err = pr.Save(cfg.SessionId)
if err != nil {
fmt.Fprintf(os.Stderr, "Failed to save state with error: %v\n", err)
}
en, err = engine.NewPersistedEngine(ctx, cfg, pr, rfs)
if err != nil {
fmt.Fprintf(os.Stderr, "engine create exited with error: %v\n", err)
os.Exit(1)
}
}
fp := path.Join(dp, sessionId)
ussdHandlers := ussd.NewHandlers(fp, &st)
rfs.AddLocalFunc("select_language", ussdHandlers.SetLanguage)
rfs.AddLocalFunc("create_account", ussdHandlers.CreateAccount)
rfs.AddLocalFunc("save_pin", ussdHandlers.SavePin)
rfs.AddLocalFunc("verify_pin", ussdHandlers.VerifyPin)
rfs.AddLocalFunc("check_identifier", ussdHandlers.CheckIdentifier)
rfs.AddLocalFunc("check_account_status", ussdHandlers.CheckAccountStatus)
rfs.AddLocalFunc("authorize_account", ussdHandlers.Authorize)
rfs.AddLocalFunc("quit", ussdHandlers.Quit)
rfs.AddLocalFunc("check_balance", ussdHandlers.CheckBalance)
rfs.AddLocalFunc("validate_recipient", ussdHandlers.ValidateRecipient)
rfs.AddLocalFunc("transaction_reset", ussdHandlers.TransactionReset)
rfs.AddLocalFunc("max_amount", ussdHandlers.MaxAmount)
rfs.AddLocalFunc("validate_amount", ussdHandlers.ValidateAmount)
rfs.AddLocalFunc("reset_transaction_amount", ussdHandlers.ResetTransactionAmount)
rfs.AddLocalFunc("get_recipient", ussdHandlers.GetRecipient)
rfs.AddLocalFunc("get_sender", ussdHandlers.GetSender)
rfs.AddLocalFunc("get_amount", ussdHandlers.GetAmount)
rfs.AddLocalFunc("reset_incorrect", ussdHandlers.ResetIncorrectPin)
rfs.AddLocalFunc("save_firstname", ussdHandlers.SaveFirstname)
rfs.AddLocalFunc("save_familyname", ussdHandlers.SaveFamilyname)
rfs.AddLocalFunc("save_gender", ussdHandlers.SaveGender)
rfs.AddLocalFunc("save_location", ussdHandlers.SaveLocation)
rfs.AddLocalFunc("save_yob", ussdHandlers.SaveYob)
rfs.AddLocalFunc("save_offerings", ussdHandlers.SaveOfferings)
rfs.AddLocalFunc("quit_with_balance", ussdHandlers.QuitWithBalance)
rfs.AddLocalFunc("reset_account_authorized", ussdHandlers.ResetAccountAuthorized)
rfs.AddLocalFunc("reset_allow_update", ussdHandlers.ResetAllowUpdate)
rfs.AddLocalFunc("get_profile_info", ussdHandlers.GetProfileInfo)
rfs.AddLocalFunc("verify_yob", ussdHandlers.VerifyYob)
rfs.AddLocalFunc("reset_incorrect_date_format", ussdHandlers.ResetIncorrectYob)
rfs.AddLocalFunc("set_reset_single_edit", ussdHandlers.SetResetSingleEdit)
rfs.AddLocalFunc("initiate_transaction", ussdHandlers.InitiateTransaction)
cont, err := en.Init(ctx)
en.SetDebugger(engine.NewSimpleDebug(nil))
if err != nil {
fmt.Fprintf(os.Stderr, "engine init exited with error: %v\n", err)
os.Exit(1)
}
if !cont {
_, err = en.WriteResult(ctx, os.Stdout)
if err != nil {
fmt.Fprintf(os.Stderr, "dead init write error: %v\n", err)
os.Exit(1)
}
err = en.Finish()
if err != nil {
fmt.Fprintf(os.Stderr, "engine finish error: %v\n", err)
os.Exit(1)
}
os.Stdout.Write([]byte{0x0a})
os.Exit(0)
}
err = engine.Loop(ctx, en, os.Stdin, os.Stdout)
if err != nil {
fmt.Fprintf(os.Stderr, "loop exited with error: %v\n", err)
os.Exit(1)
}
}

View File

@ -1,10 +1,59 @@
package config
import (
"strings"
const (
CreateAccountURL = "https://custodial.sarafu.africa/api/account/create"
TrackStatusURL = "https://custodial.sarafu.africa/api/track/"
BalanceURL = "https://custodial.sarafu.africa/api/account/status/"
"git.grassecon.net/grassrootseconomics/visedriver/env"
)
var (
defaultLanguage = "eng"
languages []string
)
var (
DbConn string
DefaultLanguage string
Languages []string
)
func setLanguage() error {
defaultLanguage = env.GetEnv("DEFAULT_LANGUAGE", defaultLanguage)
languages = strings.Split(env.GetEnv("LANGUAGES", defaultLanguage), ",")
haveDefaultLanguage := false
for i, v := range(languages) {
languages[i] = strings.ReplaceAll(v, " ", "")
if languages[i] == defaultLanguage {
haveDefaultLanguage = true
}
}
if !haveDefaultLanguage {
languages = append([]string{defaultLanguage}, languages...)
}
return nil
}
func setConn() error {
DbConn = env.GetEnv("DB_CONN", "")
return nil
}
// LoadConfig initializes the configuration values after environment variables are loaded.
func LoadConfig() error {
err := setConn()
if err != nil {
return err
}
err = setLanguage()
if err != nil {
return err
}
DefaultLanguage = defaultLanguage
Languages = languages
return nil
}

28
doc/data.md Normal file
View File

@ -0,0 +1,28 @@
# Internals
## Version
This document describes component versions:
* `urdt-ussd` `v0.5.0-beta`
* `go-vise` `v0.2.2`
## User profile data
All user profile items are stored under keys matching the user's session id, prefixed with the 8-bit value `git.defalsify.org/vise.git/db.DATATYPE_USERDATA` (32), and followed with a 16-big big-endian value subprefix.
For example, given the sessionId `+254123` and the key `git.grassecon.net/urdt-ussd/common.DATA_PUBLIC_KEY` (2) will be stored under the key:
```
0x322b3235343132330002
prefix sessionid subprefix
32 2b323534313233 0002
```
### Sub-prefixes
All sub-prefixes are defined as constants in the `git.grassecon.net/urdt-ussd/common` package. The constant names have the prefix `DATA_`
Please refer to inline godoc documentation for the `git.grassecon.net/urdt-ussd/common` package for details on each data item.

13
entry/handlers.go Normal file
View File

@ -0,0 +1,13 @@
package entry
import (
"context"
"git.defalsify.org/vise.git/resource"
"git.defalsify.org/vise.git/persist"
)
type EntryHandler interface {
Init(context.Context, string, []byte) (resource.Result, error) // HandlerFunc
Exit()
SetPersister(*persist.Persister)
}

40
env/load.go vendored Normal file
View File

@ -0,0 +1,40 @@
package env
import (
"log"
"os"
"path"
"strconv"
"github.com/joho/godotenv"
)
func LoadEnvVariables() {
LoadEnvVariablesPath(".")
}
func LoadEnvVariablesPath(dir string) {
fp := path.Join(dir, ".env")
err := godotenv.Load(fp)
if err != nil {
log.Fatal("Error loading .env file", err)
}
}
// Helper to get environment variables with a default fallback
func GetEnv(key, defaultVal string) string {
if value, exists := os.LookupEnv(key); exists {
return value
}
return defaultVal
}
// Helper to safely convert environment variables to uint
func GetEnvUint(key string, defaultVal uint) uint {
if value, exists := os.LookupEnv(key); exists {
if parsed, err := strconv.Atoi(value); err == nil && parsed >= 0 {
return uint(parsed)
}
}
return defaultVal
}

15
errors/errors.go Normal file
View File

@ -0,0 +1,15 @@
package errors
import (
"errors"
)
var (
ErrInvalidRequest = errors.New("invalid request for context")
ErrSessionMissing = errors.New("missing session")
ErrInvalidInput = errors.New("invalid input")
ErrStorage = errors.New("storage retrieval fail")
ErrEngineType = errors.New("incompatible engine")
ErrEngineInit = errors.New("engine init fail")
ErrEngineExec = errors.New("engine exec fail")
)

@ -1 +0,0 @@
Subproject commit 1f47a674d95380be8c387f410f0342eb72357df5

28
go.mod
View File

@ -1,5 +1,27 @@
module git.grassecon.net/urdt/ussd
module git.grassecon.net/grassrootseconomics/visedriver
go 1.22.6
go 1.23.0
require github.com/stretchr/testify v1.9.0 // indirect
require (
git.defalsify.org/vise.git v0.2.3-0.20250114225117-3b5fc85b650b
github.com/jackc/pgx/v5 v5.7.1
github.com/joho/godotenv v1.5.1
)
require (
github.com/barbashov/iso639-3 v0.0.0-20211020172741-1f4ffb2d8d1c // indirect
github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc // indirect
github.com/fxamacker/cbor/v2 v2.4.0 // indirect
github.com/graygnuorg/go-gdbm v0.0.0-20220711140707-71387d66dce4 // indirect
github.com/jackc/pgpassfile v1.0.0 // indirect
github.com/jackc/pgservicefile v0.0.0-20240606120523-5a60cdf6a761 // indirect
github.com/jackc/puddle/v2 v2.2.2 // indirect
github.com/mattn/kinako v0.0.0-20170717041458-332c0a7e205a // indirect
github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2 // indirect
github.com/stretchr/testify v1.9.0 // indirect
github.com/x448/float16 v0.8.4 // indirect
golang.org/x/crypto v0.27.0 // indirect
golang.org/x/sync v0.8.0 // indirect
golang.org/x/text v0.18.0 // indirect
gopkg.in/leonelquinteros/gotext.v1 v1.3.1 // indirect
)

47
go.sum
View File

@ -1,2 +1,49 @@
git.defalsify.org/vise.git v0.2.3-0.20250114225117-3b5fc85b650b h1:rwWXMtNSn7aqhb4p1oVZkCA1vC7pVdohwW61QQM8fUs=
git.defalsify.org/vise.git v0.2.3-0.20250114225117-3b5fc85b650b/go.mod h1:jyBMe1qTYUz3mmuoC9JQ/TvFeW0vTanCUcPu3H8p4Ck=
github.com/barbashov/iso639-3 v0.0.0-20211020172741-1f4ffb2d8d1c h1:H9Nm+I7Cg/YVPpEV1RzU3Wq2pjamPc/UtHDgItcb7lE=
github.com/barbashov/iso639-3 v0.0.0-20211020172741-1f4ffb2d8d1c/go.mod h1:rGod7o6KPeJ+hyBpHfhi4v7blx9sf+QsHsA7KAsdN6U=
github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc h1:U9qPSI2PIWSS1VwoXQT9A3Wy9MM3WgvqSxFWenqJduM=
github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
github.com/fxamacker/cbor/v2 v2.4.0 h1:ri0ArlOR+5XunOP8CRUowT0pSJOwhW098ZCUyskZD88=
github.com/fxamacker/cbor/v2 v2.4.0/go.mod h1:TA1xS00nchWmaBnEIxPSE5oHLuJBAVvqrtAnWBwBCVo=
github.com/graygnuorg/go-gdbm v0.0.0-20220711140707-71387d66dce4 h1:U4kkNYryi/qfbBF8gh7Vsbuz+cVmhf5kt6pE9bYYyLo=
github.com/graygnuorg/go-gdbm v0.0.0-20220711140707-71387d66dce4/go.mod h1:zpZDgZFzeq9s0MIeB1P50NIEWDFFHSFBohI/NbaTD/Y=
github.com/jackc/pgpassfile v1.0.0 h1:/6Hmqy13Ss2zCq62VdNG8tM1wchn8zjSGOBJ6icpsIM=
github.com/jackc/pgpassfile v1.0.0/go.mod h1:CEx0iS5ambNFdcRtxPj5JhEz+xB6uRky5eyVu/W2HEg=
github.com/jackc/pgservicefile v0.0.0-20240606120523-5a60cdf6a761 h1:iCEnooe7UlwOQYpKFhBabPMi4aNAfoODPEFNiAnClxo=
github.com/jackc/pgservicefile v0.0.0-20240606120523-5a60cdf6a761/go.mod h1:5TJZWKEWniPve33vlWYSoGYefn3gLQRzjfDlhSJ9ZKM=
github.com/jackc/pgx/v5 v5.7.1 h1:x7SYsPBYDkHDksogeSmZZ5xzThcTgRz++I5E+ePFUcs=
github.com/jackc/pgx/v5 v5.7.1/go.mod h1:e7O26IywZZ+naJtWWos6i6fvWK+29etgITqrqHLfoZA=
github.com/jackc/puddle/v2 v2.2.2 h1:PR8nw+E/1w0GLuRFSmiioY6UooMp6KJv0/61nB7icHo=
github.com/jackc/puddle/v2 v2.2.2/go.mod h1:vriiEXHvEE654aYKXXjOvZM39qJ0q+azkZFrfEOc3H4=
github.com/joho/godotenv v1.5.1 h1:7eLL/+HRGLY0ldzfGMeQkb7vMd0as4CfYvUVzLqw0N0=
github.com/joho/godotenv v1.5.1/go.mod h1:f4LDr5Voq0i2e/R5DDNOoa2zzDfwtkZa6DnEwAbqwq4=
github.com/mattn/kinako v0.0.0-20170717041458-332c0a7e205a h1:0Q3H0YXzMHiciXtRcM+j0jiCe8WKPQHoRgQiRTnfcLY=
github.com/mattn/kinako v0.0.0-20170717041458-332c0a7e205a/go.mod h1:CdTTBOYzS5E4mWS1N8NWP6AHI19MP0A2B18n3hLzRMk=
github.com/pashagolub/pgxmock/v4 v4.3.0 h1:DqT7fk0OCK6H0GvqtcMsLpv8cIwWqdxWgfZNLeHCb/s=
github.com/pashagolub/pgxmock/v4 v4.3.0/go.mod h1:9VoVHXwS3XR/yPtKGzwQvwZX1kzGB9sM8SviDcHDa3A=
github.com/peteole/testdata-loader v0.3.0 h1:8jckE9KcyNHgyv/VPoaljvKZE0Rqr8+dPVYH6rfNr9I=
github.com/peteole/testdata-loader v0.3.0/go.mod h1:Mt0ZbRtb56u8SLJpNP+BnQbENljMorYBpqlvt3cS83U=
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2 h1:Jamvg5psRIccs7FGNTlIRMkT8wgtp5eCXdBlqhYGL6U=
github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME=
github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI=
github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg=
github.com/stretchr/testify v1.9.0 h1:HtqpIVDClZ4nwg75+f6Lvsy/wHu+3BoSGCbBAcpTsTg=
github.com/stretchr/testify v1.9.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY=
github.com/x448/float16 v0.8.4 h1:qLwI1I70+NjRFUR3zs1JPUCgaCXSh3SW62uAKT1mSBM=
github.com/x448/float16 v0.8.4/go.mod h1:14CWIYCyZA/cWjXOioeEpHeN/83MdbZDRQHoFcYsOfg=
golang.org/x/crypto v0.27.0 h1:GXm2NjJrPaiv/h1tb2UH8QfgC/hOf/+z0p6PT8o1w7A=
golang.org/x/crypto v0.27.0/go.mod h1:1Xngt8kV6Dvbssa53Ziq6Eqn0HqbZi5Z6R0ZpwQzt70=
golang.org/x/sync v0.8.0 h1:3NFvSEYkUoMifnESzZl15y791HH1qU2xm6eCJU5ZPXQ=
golang.org/x/sync v0.8.0/go.mod h1:Czt+wKu1gCyEFDUtn0jG5QVvpJ6rzVqr5aXyt9drQfk=
golang.org/x/text v0.18.0 h1:XvMDiNzPAl0jr17s6W9lcaIhGUfUORdGCNsuLmPG224=
golang.org/x/text v0.18.0/go.mod h1:BuEKDfySbSR4drPmRPG/7iBdf8hvFMuRexcpahXilzY=
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
gopkg.in/leonelquinteros/gotext.v1 v1.3.1 h1:8d9/fdTG0kn/B7NNGV1BsEyvektXFAbkMsTZS2sFSCc=
gopkg.in/leonelquinteros/gotext.v1 v1.3.1/go.mod h1:X1WlGDeAFIYsW6GjgMm4VwUwZ2XjI7Zan2InxSUQWrU=
gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA=
gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=

View File

@ -1,112 +0,0 @@
package server
import (
"encoding/json"
"io"
"net/http"
"git.grassecon.net/urdt/ussd/config"
"git.grassecon.net/urdt/ussd/internal/models"
)
type AccountServiceInterface interface {
CheckBalance(publicKey string) (string, error)
CreateAccount() (*models.AccountResponse, error)
CheckAccountStatus(trackingId string) (string, error)
}
type AccountService struct {
}
// CheckAccountStatus retrieves the status of an account transaction based on the provided tracking ID.
//
// Parameters:
// - trackingId: A unique identifier for the account.This should be obtained from a previous call to
// CreateAccount or a similar function that returns an AccountResponse. The `trackingId` field in the
// AccountResponse struct can be used here to check the account status during a transaction.
//
//
// Returns:
// - string: The status of the transaction as a string. If there is an error during the request or processing, this will be an empty string.
// - error: An error if any occurred during the HTTP request, reading the response, or unmarshalling the JSON data.
// If no error occurs, this will be nil.
//
func (as *AccountService) CheckAccountStatus(trackingId string) (string, error) {
resp, err := http.Get(config.TrackStatusURL + trackingId)
if err != nil {
return "", err
}
defer resp.Body.Close()
body, err := io.ReadAll(resp.Body)
if err != nil {
return "", err
}
var trackResp models.TrackStatusResponse
err = json.Unmarshal(body, &trackResp)
if err != nil {
return "", err
}
status := trackResp.Result.Transaction.Status
return status, nil
}
// CheckBalance retrieves the balance for a given public key from the custodial balance API endpoint.
// Parameters:
// - publicKey: The public key associated with the account whose balance needs to be checked.
func (as *AccountService) CheckBalance(publicKey string) (string, error) {
resp, err := http.Get(config.BalanceURL + publicKey)
if err != nil {
return "0.0", err
}
defer resp.Body.Close()
body, err := io.ReadAll(resp.Body)
if err != nil {
return "0.0", err
}
var balanceResp models.BalanceResponse
err = json.Unmarshal(body, &balanceResp)
if err != nil {
return "0.0", err
}
balance := balanceResp.Result.Balance
return balance, nil
}
//CreateAccount creates a new account in the custodial system.
// Returns:
// - *models.AccountResponse: A pointer to an AccountResponse struct containing the details of the created account.
// If there is an error during the request or processing, this will be nil.
// - error: An error if any occurred during the HTTP request, reading the response, or unmarshalling the JSON data.
// If no error occurs, this will be nil.
func (as *AccountService) CreateAccount() (*models.AccountResponse, error) {
resp, err := http.Post(config.CreateAccountURL, "application/json", nil)
if err != nil {
return nil, err
}
defer resp.Body.Close()
body, err := io.ReadAll(resp.Body)
if err != nil {
return nil, err
}
var accountResp models.AccountResponse
err = json.Unmarshal(body, &accountResp)
if err != nil {
return nil, err
}
return &accountResp, nil
}

View File

@ -1,779 +0,0 @@
package ussd
import (
"bytes"
"context"
"fmt"
"path"
"regexp"
"strconv"
"strings"
"git.defalsify.org/vise.git/engine"
"git.defalsify.org/vise.git/lang"
"git.defalsify.org/vise.git/resource"
"git.defalsify.org/vise.git/state"
"git.grassecon.net/urdt/ussd/internal/handlers/server"
"git.grassecon.net/urdt/ussd/internal/models"
"git.grassecon.net/urdt/ussd/internal/utils"
"gopkg.in/leonelquinteros/gotext.v1"
)
var (
scriptDir = path.Join("services", "registration")
translationDir = path.Join(scriptDir, "locale")
)
type FSData struct {
Path string
St *state.State
}
type Handlers struct {
fs *FSData
accountFileHandler utils.AccountFileHandlerInterface
accountService server.AccountServiceInterface
}
func NewHandlers(path string, st *state.State) *Handlers {
return &Handlers{
fs: &FSData{
Path: path,
St: st,
},
accountFileHandler: utils.NewAccountFileHandler(path + "_data"),
accountService: &server.AccountService{},
}
}
// Define the regex pattern as a constant
const pinPattern = `^\d{4}$`
// isValidPIN checks whether the given input is a 4 digit number
func isValidPIN(pin string) bool {
match, _ := regexp.MatchString(pinPattern, pin)
return match
}
// SetLanguage sets the language across the menu
func (h *Handlers) SetLanguage(ctx context.Context, sym string, input []byte) (resource.Result, error) {
inputStr := string(input)
res := resource.Result{}
switch inputStr {
case "0":
res.FlagSet = []uint32{state.FLAG_LANG}
res.Content = "eng"
case "1":
res.FlagSet = []uint32{state.FLAG_LANG}
res.Content = "swa"
default:
}
res.FlagSet = append(res.FlagSet, models.USERFLAG_LANGUAGE_SET)
return res, nil
}
// CreateAccount checks if any account exists on the JSON data file, and if not
// creates an account on the API,
// sets the default values and flags
func (h *Handlers) CreateAccount(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
err := h.accountFileHandler.EnsureFileExists()
if err != nil {
return res, err
}
// if an account exists, return to prevent duplicate account creation
existingAccountData, err := h.accountFileHandler.ReadAccountData()
if existingAccountData != nil {
return res, err
}
accountResp, err := h.accountService.CreateAccount()
if err != nil {
res.FlagSet = append(res.FlagSet, models.USERFLAG_ACCOUNT_CREATION_FAILED)
return res, err
}
accountData := map[string]string{
"TrackingId": accountResp.Result.TrackingId,
"PublicKey": accountResp.Result.PublicKey,
"CustodialId": accountResp.Result.CustodialId.String(),
"Status": "PENDING",
"Gender": "Not provided",
"YOB": "Not provided",
"Location": "Not provided",
"Offerings": "Not provided",
"FirstName": "Not provided",
"FamilyName": "Not provided",
}
err = h.accountFileHandler.WriteAccountData(accountData)
if err != nil {
return res, err
}
res.FlagSet = append(res.FlagSet, models.USERFLAG_ACCOUNT_CREATED)
return res, err
}
// SavePin persists the user's PIN choice into the filesystem
func (h *Handlers) SavePin(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
accountPIN := string(input)
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
// Validate that the PIN is a 4-digit number
if !isValidPIN(accountPIN) {
res.FlagSet = append(res.FlagSet, models.USERFLAG_INCORRECTPIN)
return res, nil
}
res.FlagReset = append(res.FlagReset, models.USERFLAG_INCORRECTPIN)
accountData["AccountPIN"] = accountPIN
err = h.accountFileHandler.WriteAccountData(accountData)
if err != nil {
return res, err
}
return res, nil
}
// SetResetSingleEdit sets and resets flags to allow gradual editing of profile information.
func (h *Handlers) SetResetSingleEdit(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
menuOption := string(input)
switch menuOption {
case "2":
res.FlagReset = append(res.FlagSet, models.USERFLAG_ALLOW_UPDATE)
res.FlagSet = append(res.FlagSet, models.USERFLAG_SINGLE_EDIT)
case "3":
res.FlagReset = append(res.FlagSet, models.USERFLAG_ALLOW_UPDATE)
res.FlagSet = append(res.FlagSet, models.USERFLAG_SINGLE_EDIT)
case "4":
res.FlagReset = append(res.FlagSet, models.USERFLAG_ALLOW_UPDATE)
res.FlagSet = append(res.FlagSet, models.USERFLAG_SINGLE_EDIT)
default:
res.FlagReset = append(res.FlagReset, models.USERFLAG_SINGLE_EDIT)
}
return res, nil
}
// VerifyPin checks whether the confirmation PIN is similar to the account PIN
// If similar, it sets the USERFLAG_PIN_SET flag allowing the user
// to access the main menu
func (h *Handlers) VerifyPin(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
if bytes.Equal(input, []byte(accountData["AccountPIN"])) {
res.FlagSet = []uint32{models.USERFLAG_VALIDPIN}
res.FlagReset = []uint32{models.USERFLAG_PINMISMATCH}
res.FlagSet = append(res.FlagSet, models.USERFLAG_PIN_SET)
} else {
res.FlagSet = []uint32{models.USERFLAG_PINMISMATCH}
}
return res, nil
}
//codeFromCtx retrieves language codes from the context that can be used for handling translations
func codeFromCtx(ctx context.Context) string {
var code string
engine.Logg.DebugCtxf(ctx, "in msg", "ctx", ctx, "val", code)
if ctx.Value("Language") != nil {
lang := ctx.Value("Language").(lang.Language)
code = lang.Code
}
return code
}
// SaveFirstname updates the first name in a JSON data file with the provided input.
func (h *Handlers) SaveFirstname(cxt context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
if len(input) > 0 {
name := string(input)
accountData["FirstName"] = name
err = h.accountFileHandler.WriteAccountData(accountData)
if err != nil {
return res, err
}
}
return res, nil
}
// SaveFamilyname updates the family name in a JSON data file with the provided input.
func (h *Handlers) SaveFamilyname(cxt context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
if len(input) > 0 {
secondname := string(input)
accountData["FamilyName"] = secondname
err = h.accountFileHandler.WriteAccountData(accountData)
if err != nil {
return res, err
}
}
return res, nil
}
// SaveYOB updates the Year of Birth(YOB) in a JSON data file with the provided input.
func (h *Handlers) SaveYob(cxt context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
yob := string(input)
if len(yob) == 4 {
yob := string(input)
accountData["YOB"] = yob
err = h.accountFileHandler.WriteAccountData(accountData)
if err != nil {
return res, err
}
}
return res, nil
}
// SaveLocation updates the location in a JSON data file with the provided input.
func (h *Handlers) SaveLocation(cxt context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
if len(input) > 0 {
location := string(input)
accountData["Location"] = location
err = h.accountFileHandler.WriteAccountData(accountData)
if err != nil {
return res, err
}
}
return res, nil
}
// SaveGender updates the gender in a JSON data file with the provided input.
func (h *Handlers) SaveGender(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
if len(input) > 0 {
gender := string(input)
switch gender {
case "1":
gender = "Male"
case "2":
gender = "Female"
case "3":
gender = "Unspecified"
}
accountData["Gender"] = gender
err = h.accountFileHandler.WriteAccountData(accountData)
if err != nil {
return res, err
}
}
return res, nil
}
// SaveOfferings updates the offerings(goods and services provided by the user) in a JSON data file with the provided input.
func (h *Handlers) SaveOfferings(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
if len(input) > 0 {
offerings := string(input)
accountData["Offerings"] = offerings
err = h.accountFileHandler.WriteAccountData(accountData)
if err != nil {
return res, err
}
}
return res, nil
}
// ResetAllowUpdate resets the allowupdate flag that allows a user to update profile data.
func (h *Handlers) ResetAllowUpdate(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
res.FlagReset = append(res.FlagReset, models.USERFLAG_ALLOW_UPDATE)
return res, nil
}
// ResetAccountAuthorized resets the account authorization flag after a successful PIN entry.
func (h *Handlers) ResetAccountAuthorized(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
res.FlagReset = append(res.FlagReset, models.USERFLAG_ACCOUNT_AUTHORIZED)
return res, nil
}
// CheckIdentifier retrieves the PublicKey from the JSON data file.
func (h *Handlers) CheckIdentifier(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
res.Content = accountData["PublicKey"]
return res, nil
}
// Authorize attempts to unlock the next sequential nodes by verifying the provided PIN against the already set PIN.
// It sets the required flags that control the flow.
func (h *Handlers) Authorize(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
pin := string(input)
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
if len(input) == 4 {
if pin != accountData["AccountPIN"] {
res.FlagSet = append(res.FlagSet, models.USERFLAG_INCORRECTPIN)
res.FlagReset = append(res.FlagReset, models.USERFLAG_ACCOUNT_AUTHORIZED)
return res, nil
}
if h.fs.St.MatchFlag(models.USERFLAG_ACCOUNT_AUTHORIZED, false) {
res.FlagReset = append(res.FlagReset, models.USERFLAG_INCORRECTPIN)
res.FlagSet = append(res.FlagSet, models.USERFLAG_ALLOW_UPDATE)
res.FlagSet = append(res.FlagSet, models.USERFLAG_ACCOUNT_AUTHORIZED)
} else {
res.FlagSet = append(res.FlagSet, models.USERFLAG_ALLOW_UPDATE)
res.FlagReset = append(res.FlagReset, models.USERFLAG_ACCOUNT_AUTHORIZED)
}
}
return res, nil
}
// ResetIncorrectPin resets the incorrect pin flag after a new PIN attempt.
func (h *Handlers) ResetIncorrectPin(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
res.FlagReset = append(res.FlagReset, models.USERFLAG_INCORRECTPIN)
return res, nil
}
// CheckAccountStatus queries the API using the TrackingId and sets flags
// based on the account status
func (h *Handlers) CheckAccountStatus(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
status, err := h.accountService.CheckAccountStatus(accountData["TrackingId"])
if err != nil {
fmt.Println("Error checking account status:", err)
return res, nil
}
accountData["Status"] = status
if status == "SUCCESS" {
res.FlagSet = append(res.FlagSet, models.USERFLAG_ACCOUNT_SUCCESS)
res.FlagReset = append(res.FlagReset, models.USERFLAG_ACCOUNT_PENDING)
} else {
res.FlagReset = append(res.FlagSet, models.USERFLAG_ACCOUNT_SUCCESS)
res.FlagSet = append(res.FlagReset, models.USERFLAG_ACCOUNT_PENDING)
}
err = h.accountFileHandler.WriteAccountData(accountData)
if err != nil {
return res, err
}
return res, nil
}
// Quit displays the Thank you message and exits the menu
func (h *Handlers) Quit(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
code := codeFromCtx(ctx)
l := gotext.NewLocale(translationDir, code)
l.AddDomain("default")
res.Content = l.Get("Thank you for using Sarafu. Goodbye!")
res.FlagReset = append(res.FlagReset, models.USERFLAG_ACCOUNT_AUTHORIZED)
return res, nil
}
// VerifyYob verifies the length of the given input
func (h *Handlers) VerifyYob(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
date := string(input)
_, err := strconv.Atoi(date)
if err != nil {
// If conversion fails, input is not numeric
res.FlagSet = append(res.FlagSet, models.USERFLAG_INCORRECTDATEFORMAT)
return res, nil
}
if len(date) == 4 {
res.FlagReset = append(res.FlagReset, models.USERFLAG_INCORRECTDATEFORMAT)
} else {
res.FlagSet = append(res.FlagSet, models.USERFLAG_INCORRECTDATEFORMAT)
}
return res, nil
}
// ResetIncorrectYob resets the incorrect date format after a new attempt
func (h *Handlers) ResetIncorrectYob(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
res.FlagReset = append(res.FlagReset, models.USERFLAG_INCORRECTDATEFORMAT)
return res, nil
}
// CheckBalance retrieves the balance from the API using the "PublicKey" and sets
// the balance as the result content
func (h *Handlers) CheckBalance(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
balance, err := h.accountService.CheckBalance(accountData["PublicKey"])
if err != nil {
return res, nil
}
res.Content = balance
return res, nil
}
// ValidateRecipient validates that the given input is a valid phone number.
func (h *Handlers) ValidateRecipient(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
recipient := string(input)
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
if recipient != "0" {
// mimic invalid number check
if recipient == "000" {
res.FlagSet = append(res.FlagSet, models.USERFLAG_INVALID_RECIPIENT)
res.Content = recipient
return res, nil
}
accountData["Recipient"] = recipient
err = h.accountFileHandler.WriteAccountData(accountData)
if err != nil {
return res, err
}
}
return res, nil
}
// TransactionReset resets the previous transaction data (Recipient and Amount)
// as well as the invalid flags
func (h *Handlers) TransactionReset(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
// reset the transaction
accountData["Recipient"] = ""
accountData["Amount"] = ""
err = h.accountFileHandler.WriteAccountData(accountData)
if err != nil {
return res, err
}
res.FlagReset = append(res.FlagReset, models.USERFLAG_INVALID_RECIPIENT, models.USERFLAG_INVALID_RECIPIENT_WITH_INVITE)
return res, nil
}
// ResetTransactionAmount resets the transaction amount and invalid flag
func (h *Handlers) ResetTransactionAmount(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
// reset the amount
accountData["Amount"] = ""
err = h.accountFileHandler.WriteAccountData(accountData)
if err != nil {
return res, err
}
res.FlagReset = append(res.FlagReset, models.USERFLAG_INVALID_AMOUNT)
return res, nil
}
// MaxAmount gets the current balance from the API and sets it as
// the result content.
func (h *Handlers) MaxAmount(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
balance, err := h.accountService.CheckBalance(accountData["PublicKey"])
if err != nil {
return res, nil
}
res.Content = balance
return res, nil
}
// ValidateAmount ensures that the given input is a valid amount and that
// it is not more than the current balance.
func (h *Handlers) ValidateAmount(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
amountStr := string(input)
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
balanceStr, err := h.accountService.CheckBalance(accountData["PublicKey"])
if err != nil {
return res, err
}
res.Content = balanceStr
// Parse the balance
balanceParts := strings.Split(balanceStr, " ")
if len(balanceParts) != 2 {
return res, fmt.Errorf("unexpected balance format: %s", balanceStr)
}
balanceValue, err := strconv.ParseFloat(balanceParts[0], 64)
if err != nil {
return res, fmt.Errorf("failed to parse balance: %v", err)
}
// Extract numeric part from input
re := regexp.MustCompile(`^(\d+(\.\d+)?)\s*(?:CELO)?$`)
matches := re.FindStringSubmatch(strings.TrimSpace(amountStr))
if len(matches) < 2 {
res.FlagSet = append(res.FlagSet, models.USERFLAG_INVALID_AMOUNT)
res.Content = amountStr
return res, nil
}
inputAmount, err := strconv.ParseFloat(matches[1], 64)
if err != nil {
res.FlagSet = append(res.FlagSet, models.USERFLAG_INVALID_AMOUNT)
res.Content = amountStr
return res, nil
}
if inputAmount > balanceValue {
res.FlagSet = append(res.FlagSet, models.USERFLAG_INVALID_AMOUNT)
res.Content = amountStr
return res, nil
}
res.Content = fmt.Sprintf("%.3f", inputAmount) // Format to 3 decimal places
accountData["Amount"] = res.Content
err = h.accountFileHandler.WriteAccountData(accountData)
if err != nil {
return res, err
}
return res, nil
}
// GetRecipient returns the transaction recipient from a JSON data file.
func (h *Handlers) GetRecipient(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
res.Content = accountData["Recipient"]
return res, nil
}
// GetProfileInfo retrieves and formats the profile information of a user from a JSON data file.
func (h *Handlers) GetProfileInfo(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
var age string
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
var name string
if accountData["FirstName"] == "Not provided" || accountData["FamilyName"] == "Not provided" {
name = "Not provided"
} else {
name = accountData["FirstName"] + " " + accountData["FamilyName"]
}
gender := accountData["Gender"]
yob := accountData["YOB"]
location := accountData["Location"]
offerings := accountData["Offerings"]
if yob == "Not provided" {
age = "Not provided"
} else {
ageInt, err := strconv.Atoi(yob)
if err != nil {
return res, nil
}
age = strconv.Itoa(utils.CalculateAgeWithYOB(ageInt))
}
formattedData := fmt.Sprintf("Name: %s\nGender: %s\nAge: %s\nLocation: %s\nYou provide: %s\n", name, gender, age, location, offerings)
res.Content = formattedData
return res, nil
}
// GetSender retrieves the public key from a JSON data file.
func (h *Handlers) GetSender(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
res.Content = accountData["PublicKey"]
return res, nil
}
// GetAmount retrieves the amount from a JSON data file.
func (h *Handlers) GetAmount(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
res.Content = accountData["Amount"]
return res, nil
}
// QuickWithBalance retrieves the balance for a given public key from the custodial balance API endpoint before
// gracefully exiting the session.
func (h *Handlers) QuitWithBalance(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
code := codeFromCtx(ctx)
l := gotext.NewLocale(translationDir, code)
l.AddDomain("default")
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
balance, err := h.accountService.CheckBalance(accountData["PublicKey"])
if err != nil {
return res, nil
}
res.Content = l.Get("Your account balance is %s", balance)
res.FlagReset = append(res.FlagReset, models.USERFLAG_ACCOUNT_AUTHORIZED)
return res, nil
}
// InitiateTransaction returns a confirmation and resets the transaction data
// on the JSON file.
func (h *Handlers) InitiateTransaction(ctx context.Context, sym string, input []byte) (resource.Result, error) {
res := resource.Result{}
code := codeFromCtx(ctx)
l := gotext.NewLocale(translationDir, code)
l.AddDomain("default")
accountData, err := h.accountFileHandler.ReadAccountData()
if err != nil {
return res, err
}
// TODO
// Use the amount, recipient and sender to call the API and initialize the transaction
res.Content = l.Get("Your request has been sent. %s will receive %s from %s.", accountData["Recipient"], accountData["Amount"], accountData["PublicKey"])
// reset the transaction
accountData["Recipient"] = ""
accountData["Amount"] = ""
err = h.accountFileHandler.WriteAccountData(accountData)
if err != nil {
return res, err
}
res.FlagReset = append(res.FlagReset, models.USERFLAG_ACCOUNT_AUTHORIZED)
return res, nil
}

View File

@ -1,878 +0,0 @@
package ussd
import (
"context"
"encoding/json"
"os"
"path/filepath"
"testing"
"git.defalsify.org/vise.git/resource"
"git.grassecon.net/urdt/ussd/internal/handlers/ussd/mocks"
"git.grassecon.net/urdt/ussd/internal/models"
"git.grassecon.net/urdt/ussd/internal/utils"
"github.com/alecthomas/assert/v2"
"github.com/stretchr/testify/mock"
)
// MockAccountService implements AccountServiceInterface for testing
type MockAccountService struct {
mock.Mock
}
func (m *MockAccountService) CreateAccount() (*models.AccountResponse, error) {
args := m.Called()
return args.Get(0).(*models.AccountResponse), args.Error(1)
}
func (m *MockAccountService) CheckBalance(publicKey string) (string, error) {
args := m.Called(publicKey)
return args.String(0), args.Error(1)
}
func (m *MockAccountService) CheckAccountStatus(trackingId string) (string, error) {
args := m.Called(trackingId)
return args.String(0), args.Error(1)
}
func TestCreateAccount(t *testing.T) {
// Setup
tempDir, err := os.MkdirTemp("", "test_create_account")
if err != nil {
t.Fatalf("Failed to create temp directory: %v", err)
}
defer os.RemoveAll(tempDir) // Clean up after the test run
sessionID := "07xxxxxxxx"
// Set up the data file path using the session ID
accountFilePath := filepath.Join(tempDir, sessionID+"_data")
// Initialize account file handler
accountFileHandler := utils.NewAccountFileHandler(accountFilePath)
// Create a mock account service
mockAccountService := &MockAccountService{}
mockAccountResponse := &models.AccountResponse{
Ok: true,
Result: struct {
CustodialId json.Number `json:"custodialId"`
PublicKey string `json:"publicKey"`
TrackingId string `json:"trackingId"`
}{
CustodialId: "test-custodial-id",
PublicKey: "test-public-key",
TrackingId: "test-tracking-id",
},
}
// Set up expectations for the mock account service
mockAccountService.On("CreateAccount").Return(mockAccountResponse, nil)
// Initialize Handlers with mock account service
h := &Handlers{
fs: &FSData{Path: accountFilePath},
accountFileHandler: accountFileHandler,
accountService: mockAccountService,
}
tests := []struct {
name string
existingData map[string]string
expectedResult resource.Result
expectedData map[string]string
}{
{
name: "New account creation",
existingData: nil,
expectedResult: resource.Result{
FlagSet: []uint32{models.USERFLAG_ACCOUNT_CREATED},
},
expectedData: map[string]string{
"TrackingId": "test-tracking-id",
"PublicKey": "test-public-key",
"CustodialId": "test-custodial-id",
"Status": "PENDING",
"Gender": "Not provided",
"YOB": "Not provided",
"Location": "Not provided",
"Offerings": "Not provided",
"FirstName": "Not provided",
"FamilyName": "Not provided",
},
},
{
name: "Existing account",
existingData: map[string]string{
"TrackingId": "test-tracking-id",
"PublicKey": "test-public-key",
"CustodialId": "test-custodial-id",
"Status": "PENDING",
"Gender": "Not provided",
"YOB": "Not provided",
"Location": "Not provided",
"Offerings": "Not provided",
"FirstName": "Not provided",
"FamilyName": "Not provided",
},
expectedResult: resource.Result{},
expectedData: map[string]string{
"TrackingId": "test-tracking-id",
"PublicKey": "test-public-key",
"CustodialId": "test-custodial-id",
"Status": "PENDING",
"Gender": "Not provided",
"YOB": "Not provided",
"Location": "Not provided",
"Offerings": "Not provided",
"FirstName": "Not provided",
"FamilyName": "Not provided",
},
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
// Set up the data file path using the session ID
accountFilePath := filepath.Join(tempDir, sessionID+"_data")
// Setup existing data if any
if tt.existingData != nil {
data, _ := json.Marshal(tt.existingData)
err := os.WriteFile(accountFilePath, data, 0644)
if err != nil {
t.Fatalf("Failed to write existing data: %v", err)
}
}
// Call the function
result, err := h.CreateAccount(context.Background(), "", nil)
// Check for errors
if err != nil {
t.Fatalf("CreateAccount returned an error: %v", err)
}
// Check the result
if len(result.FlagSet) != len(tt.expectedResult.FlagSet) {
t.Errorf("Expected %d flags, got %d", len(tt.expectedResult.FlagSet), len(result.FlagSet))
}
for i, flag := range tt.expectedResult.FlagSet {
if result.FlagSet[i] != flag {
t.Errorf("Expected flag %d, got %d", flag, result.FlagSet[i])
}
}
// Check the stored data
data, err := os.ReadFile(accountFilePath)
if err != nil {
t.Fatalf("Failed to read account data file: %v", err)
}
var storedData map[string]string
err = json.Unmarshal(data, &storedData)
if err != nil {
t.Fatalf("Failed to unmarshal stored data: %v", err)
}
for key, expectedValue := range tt.expectedData {
if storedValue, ok := storedData[key]; !ok || storedValue != expectedValue {
t.Errorf("Expected %s to be %s, got %s", key, expectedValue, storedValue)
}
}
})
}
}
func TestCreateAccount_Success(t *testing.T) {
mockAccountFileHandler := new(mocks.MockAccountFileHandler)
mockCreateAccountService := new(mocks.MockAccountService)
mockAccountFileHandler.On("EnsureFileExists").Return(nil)
// Mock that no account data exists
mockAccountFileHandler.On("ReadAccountData").Return(nil, nil)
// Define expected account response after api call
expectedAccountResp := &models.AccountResponse{
Ok: true,
Result: struct {
CustodialId json.Number `json:"custodialId"`
PublicKey string `json:"publicKey"`
TrackingId string `json:"trackingId"`
}{
CustodialId: "12",
PublicKey: "0x8E0XSCSVA",
TrackingId: "d95a7e83-196c-4fd0-866fSGAGA",
},
}
mockCreateAccountService.On("CreateAccount").Return(expectedAccountResp, nil)
// Mock WriteAccountData to not error
mockAccountFileHandler.On("WriteAccountData", mock.Anything).Return(nil)
handlers := &Handlers{
accountService: mockCreateAccountService,
}
actualResponse, err := handlers.accountService.CreateAccount()
// Assert results
assert.NoError(t, err)
assert.Equal(t, expectedAccountResp.Ok, true)
assert.Equal(t, expectedAccountResp, actualResponse)
}
func TestSavePin(t *testing.T) {
// Setup
tempDir, err := os.MkdirTemp("", "test_save_pin")
if err != nil {
t.Fatalf("Failed to create temp directory: %v", err)
}
defer os.RemoveAll(tempDir)
sessionID := "07xxxxxxxx"
// Set up the data file path using the session ID
accountFilePath := filepath.Join(tempDir, sessionID+"_data")
initialAccountData := map[string]string{
"TrackingId": "test-tracking-id",
"PublicKey": "test-public-key",
}
data, _ := json.Marshal(initialAccountData)
err = os.WriteFile(accountFilePath, data, 0644)
if err != nil {
t.Fatalf("Failed to write initial account data: %v", err)
}
// Create a new AccountFileHandler and set it in the Handlers struct
accountFileHandler := utils.NewAccountFileHandler(accountFilePath)
h := &Handlers{
accountFileHandler: accountFileHandler,
}
tests := []struct {
name string
input []byte
expectedFlags []uint32
expectedData map[string]string
expectedErrors bool
}{
{
name: "Valid PIN",
input: []byte("1234"),
expectedFlags: []uint32{},
expectedData: map[string]string{
"TrackingId": "test-tracking-id",
"PublicKey": "test-public-key",
"AccountPIN": "1234",
},
},
{
name: "Invalid PIN - non-numeric",
input: []byte("12ab"),
expectedFlags: []uint32{models.USERFLAG_INCORRECTPIN},
expectedData: initialAccountData, // No changes expected
expectedErrors: false,
},
{
name: "Invalid PIN - less than 4 digits",
input: []byte("123"),
expectedFlags: []uint32{models.USERFLAG_INCORRECTPIN},
expectedData: initialAccountData, // No changes expected
expectedErrors: false,
},
{
name: "Invalid PIN - more than 4 digits",
input: []byte("12345"),
expectedFlags: []uint32{models.USERFLAG_INCORRECTPIN},
expectedData: initialAccountData, // No changes expected
expectedErrors: false,
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
// Ensure the file exists before running the test
err := accountFileHandler.EnsureFileExists()
if err != nil {
t.Fatalf("Failed to ensure account file exists: %v", err)
}
result, err := h.SavePin(context.Background(), "", tt.input)
if err != nil && !tt.expectedErrors {
t.Fatalf("SavePin returned an unexpected error: %v", err)
}
if len(result.FlagSet) != len(tt.expectedFlags) {
t.Errorf("Expected %d flags, got %d", len(tt.expectedFlags), len(result.FlagSet))
}
for i, flag := range tt.expectedFlags {
if result.FlagSet[i] != flag {
t.Errorf("Expected flag %d, got %d", flag, result.FlagSet[i])
}
}
data, err := os.ReadFile(accountFilePath)
if err != nil {
t.Fatalf("Failed to read account data file: %v", err)
}
var storedData map[string]string
err = json.Unmarshal(data, &storedData)
if err != nil {
t.Fatalf("Failed to unmarshal stored data: %v", err)
}
for key, expectedValue := range tt.expectedData {
if storedValue, ok := storedData[key]; !ok || storedValue != expectedValue {
t.Errorf("Expected %s to be %s, got %s", key, expectedValue, storedValue)
}
}
})
}
}
func TestSaveLocation(t *testing.T) {
// Create a new instance of MockAccountFileHandler
mockFileHandler := new(mocks.MockAccountFileHandler)
// Define test cases
tests := []struct {
name string
input []byte
existingData map[string]string
writeError error
expectedResult resource.Result
expectedError error
}{
{
name: "Successful Save",
input: []byte("Mombasa"),
existingData: map[string]string{"Location": "Mombasa"},
writeError: nil,
expectedResult: resource.Result{},
expectedError: nil,
},
{
name: "Empty location input",
input: []byte{},
existingData: map[string]string{"OtherKey": "OtherValue"},
writeError: nil,
expectedResult: resource.Result{},
expectedError: nil,
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
// Set up the mock expectations
mockFileHandler.On("ReadAccountData").Return(tt.existingData, tt.expectedError)
if tt.expectedError == nil && len(tt.input) > 0 {
mockFileHandler.On("WriteAccountData", mock.MatchedBy(func(data map[string]string) bool {
return data["Location"] == string(tt.input)
})).Return(tt.writeError)
} else if len(tt.input) == 0 {
// For empty input, no WriteAccountData call should be made
mockFileHandler.On("WriteAccountData", mock.Anything).Maybe().Return(tt.writeError)
return
}
// Create the Handlers instance with the mock file handler
h := &Handlers{
accountFileHandler: mockFileHandler,
}
// Call Save Location
result, err := h.SaveLocation(context.Background(), "save_location", tt.input)
if err != nil {
t.Fatalf("Failed to save location with error: %v", err)
}
savedData, err := h.accountFileHandler.ReadAccountData()
if err == nil {
//Assert that the input provided is what was saved into the file
assert.Equal(t, string(tt.input), savedData["Location"])
}
// Assert the results
assert.Equal(t, tt.expectedResult, result)
assert.Equal(t, tt.expectedError, err)
// Assert all expectations were met
mockFileHandler.AssertExpectations(t)
})
}
}
func TestSaveFirstname(t *testing.T) {
// Create a new instance of MockAccountFileHandler
mockFileHandler := new(mocks.MockAccountFileHandler)
// Define test cases
tests := []struct {
name string
input []byte
existingData map[string]string
writeError error
expectedResult resource.Result
expectedError error
}{
{
name: "Successful Save",
input: []byte("Joe"),
existingData: map[string]string{"Name": "Joe"},
writeError: nil,
expectedResult: resource.Result{},
expectedError: nil,
},
{
name: "Empty Input",
input: []byte{},
existingData: map[string]string{"OtherKey": "OtherValue"},
writeError: nil,
expectedError: nil,
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
// Set up the mock expectations
mockFileHandler.On("ReadAccountData").Return(tt.existingData, tt.expectedError)
if tt.expectedError == nil && len(tt.input) > 0 {
mockFileHandler.On("WriteAccountData", mock.MatchedBy(func(data map[string]string) bool {
return data["FirstName"] == string(tt.input)
})).Return(tt.writeError)
} else if len(tt.input) == 0 {
// For empty input, no WriteAccountData call should be made
mockFileHandler.On("WriteAccountData", mock.Anything).Maybe().Return(tt.writeError)
return
}
// Create the Handlers instance with the mock file handler
h := &Handlers{
accountFileHandler: mockFileHandler,
}
// Call save location
result, err := h.SaveFirstname(context.Background(), "save_location", tt.input)
if err != nil {
t.Fatalf("Failed to save first name with error: %v", err)
}
savedData, err := h.accountFileHandler.ReadAccountData()
if err == nil {
//Assert that the input provided is what was saved into the file
assert.Equal(t, string(tt.input), savedData["FirstName"])
}
// Assert the results
assert.Equal(t, tt.expectedResult, result)
assert.Equal(t, tt.expectedError, err)
// Assert all expectations were met
mockFileHandler.AssertExpectations(t)
})
}
}
func TestSaveFamilyName(t *testing.T) {
// Create a new instance of MockAccountFileHandler
mockFileHandler := new(mocks.MockAccountFileHandler)
// Define test cases
tests := []struct {
name string
input []byte
existingData map[string]string
writeError error
expectedResult resource.Result
expectedError error
}{
{
name: "Successful Save",
input: []byte("Doe"),
existingData: map[string]string{"FamilyName": "Doe"},
writeError: nil,
expectedResult: resource.Result{},
expectedError: nil,
},
{
name: "Empty Input",
input: []byte{},
existingData: map[string]string{"FamilyName": "Doe"},
writeError: nil,
expectedError: nil,
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
// Set up the mock expectations
mockFileHandler.On("ReadAccountData").Return(tt.existingData, tt.expectedError)
if tt.expectedError == nil && len(tt.input) > 0 {
mockFileHandler.On("WriteAccountData", mock.MatchedBy(func(data map[string]string) bool {
return data["FamilyName"] == string(tt.input)
})).Return(tt.writeError)
} else if len(tt.input) == 0 {
// For empty input, no WriteAccountData call should be made
mockFileHandler.On("WriteAccountData", mock.Anything).Maybe().Return(tt.writeError)
return
}
// Create the Handlers instance with the mock file handler
h := &Handlers{
accountFileHandler: mockFileHandler,
}
// Call save familyname
result, err := h.SaveFamilyname(context.Background(), "save_familyname", tt.input)
if err != nil {
t.Fatalf("Failed to save family name with error: %v", err)
}
savedData, err := h.accountFileHandler.ReadAccountData()
if err == nil {
//Assert that the input provided is what was saved into the file
assert.Equal(t, string(tt.input), savedData["FamilyName"])
}
// Assert the results
assert.Equal(t, tt.expectedResult, result)
assert.Equal(t, tt.expectedError, err)
// Assert all expectations were met
mockFileHandler.AssertExpectations(t)
})
}
}
func TestSaveYOB(t *testing.T) {
// Create a new instance of MockAccountFileHandler
mockFileHandler := new(mocks.MockAccountFileHandler)
// Define test cases
tests := []struct {
name string
input []byte
existingData map[string]string
writeError error
expectedResult resource.Result
expectedError error
}{
{
name: "Successful Save",
input: []byte("2006"),
existingData: map[string]string{"": ""},
writeError: nil,
expectedResult: resource.Result{},
expectedError: nil,
},
{
name: "YOB less than 4 digits(invalid date entry)",
input: []byte{},
existingData: map[string]string{"": ""},
writeError: nil,
expectedError: nil,
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
// Set up the mock expectations
mockFileHandler.On("ReadAccountData").Return(tt.existingData, tt.expectedError)
if tt.expectedError == nil && len(tt.input) > 0 {
mockFileHandler.On("WriteAccountData", mock.MatchedBy(func(data map[string]string) bool {
return data["YOB"] == string(tt.input)
})).Return(tt.writeError)
} else if len(tt.input) != 4 {
// For input whose input is not a valid yob, no WriteAccountData call should be made
mockFileHandler.On("WriteAccountData", mock.Anything).Maybe().Return(tt.writeError)
return
}
// Create the Handlers instance with the mock file handler
h := &Handlers{
accountFileHandler: mockFileHandler,
}
// Call save yob
result, err := h.SaveYob(context.Background(), "save_yob", tt.input)
if err != nil {
t.Fatalf("Failed to save family name with error: %v", err)
}
savedData, err := h.accountFileHandler.ReadAccountData()
if err == nil {
//Assert that the input provided is what was saved into the file
assert.Equal(t, string(tt.input), savedData["YOB"])
}
// Assert the results
assert.Equal(t, tt.expectedResult, result)
assert.Equal(t, tt.expectedError, err)
// Assert all expectations were met
mockFileHandler.AssertExpectations(t)
})
}
}
func TestSaveOfferings(t *testing.T) {
// Create a new instance of MockAccountFileHandler
mockFileHandler := new(mocks.MockAccountFileHandler)
// Define test cases
tests := []struct {
name string
input []byte
existingData map[string]string
writeError error
expectedResult resource.Result
expectedError error
}{
{
name: "Successful Save",
input: []byte("Bananas"),
existingData: map[string]string{"": ""},
writeError: nil,
expectedResult: resource.Result{},
expectedError: nil,
},
{
name: "Empty input",
input: []byte{},
existingData: map[string]string{"": ""},
writeError: nil,
expectedError: nil,
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
// Set up the mock expectations
mockFileHandler.On("ReadAccountData").Return(tt.existingData, tt.expectedError)
if tt.expectedError == nil && len(tt.input) > 0 {
mockFileHandler.On("WriteAccountData", mock.MatchedBy(func(data map[string]string) bool {
return data["Offerings"] == string(tt.input)
})).Return(tt.writeError)
} else if len(tt.input) != 4 {
// For input whose input is not a valid yob, no WriteAccountData call should be made
mockFileHandler.On("WriteAccountData", mock.Anything).Maybe().Return(tt.writeError)
return
}
// Create the Handlers instance with the mock file handler
h := &Handlers{
accountFileHandler: mockFileHandler,
}
// Call save yob
result, err := h.SaveOfferings(context.Background(), "save_offerings", tt.input)
if err != nil {
t.Fatalf("Failed to save offerings with error: %v", err)
}
savedData, err := h.accountFileHandler.ReadAccountData()
if err == nil {
//Assert that the input provided is what was saved into the file
assert.Equal(t, string(tt.input), savedData["Offerings"])
}
// Assert the results
assert.Equal(t, tt.expectedResult, result)
assert.Equal(t, tt.expectedError, err)
// Assert all expectations were met
mockFileHandler.AssertExpectations(t)
})
}
}
func TestSaveGender(t *testing.T) {
// Create a new instance of MockAccountFileHandler
mockFileHandler := new(mocks.MockAccountFileHandler)
// Define test cases
tests := []struct {
name string
input []byte
existingData map[string]string
writeError error
expectedResult resource.Result
expectedError error
expectedGender string
}{
{
name: "Successful Save - Male",
input: []byte("1"),
existingData: map[string]string{"OtherKey": "OtherValue"},
writeError: nil,
expectedResult: resource.Result{},
expectedError: nil,
expectedGender: "Male",
},
{
name: "Successful Save - Female",
input: []byte("2"),
existingData: map[string]string{"OtherKey": "OtherValue"},
writeError: nil,
expectedResult: resource.Result{},
expectedError: nil,
expectedGender: "Female",
},
{
name: "Successful Save - Unspecified",
input: []byte("3"),
existingData: map[string]string{"OtherKey": "OtherValue"},
writeError: nil,
expectedResult: resource.Result{},
expectedError: nil,
expectedGender: "Unspecified",
},
{
name: "Empty Input",
input: []byte{},
existingData: map[string]string{"OtherKey": "OtherValue"},
writeError: nil,
expectedResult: resource.Result{},
expectedError: nil,
expectedGender: "",
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
// Set up the mock expectations
mockFileHandler.On("ReadAccountData").Return(tt.existingData, tt.expectedError)
if tt.expectedError == nil && len(tt.input) > 0 {
mockFileHandler.On("WriteAccountData", mock.MatchedBy(func(data map[string]string) bool {
return data["Gender"] == tt.expectedGender
})).Return(tt.writeError)
} else if len(tt.input) == 0 {
// For empty input, no WriteAccountData call should be made
mockFileHandler.On("WriteAccountData", mock.Anything).Maybe().Return(tt.writeError)
}
// Create the Handlers instance with the mock file handler
h := &Handlers{
accountFileHandler: mockFileHandler,
}
// Call the method
result, err := h.SaveGender(context.Background(), "save_gender", tt.input)
// Assert the results
assert.Equal(t, tt.expectedResult, result)
assert.Equal(t, tt.expectedError, err)
// Verify WriteAccountData was called with the expected data
if len(tt.input) > 0 && tt.expectedError == nil {
mockFileHandler.AssertCalled(t, "WriteAccountData", mock.MatchedBy(func(data map[string]string) bool {
return data["Gender"] == tt.expectedGender
}))
}
// Assert all expectations were met
mockFileHandler.AssertExpectations(t)
})
}
}
func TestGetSender(t *testing.T) {
mockAccountFileHandler := new(mocks.MockAccountFileHandler)
h := &Handlers{
accountFileHandler: mockAccountFileHandler,
}
tests := []struct {
name string
expectedResult resource.Result
accountData map[string]string
}{
{
name: "Valid public key",
expectedResult: resource.Result{
Content: "test-public-key",
},
accountData: map[string]string{
"PublicKey": "test-public-key",
},
},
{
name: "Missing public key",
expectedResult: resource.Result{
Content: "",
},
accountData: map[string]string{},
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
// Reset the mock state
mockAccountFileHandler.Mock = mock.Mock{}
mockAccountFileHandler.On("ReadAccountData").Return(tt.accountData, nil)
result, err := h.GetSender(context.Background(), "", nil)
if err != nil {
t.Fatalf("Error occurred: %v", err)
}
assert.Equal(t, tt.expectedResult.Content, result.Content)
mockAccountFileHandler.AssertCalled(t, "ReadAccountData")
})
}
}
func TestGetAmount(t *testing.T) {
mockAccountFileHandler := new(mocks.MockAccountFileHandler)
h := &Handlers{
accountFileHandler: mockAccountFileHandler,
}
tests := []struct {
name string
expectedResult resource.Result
accountData map[string]string
}{
{
name: "Valid amount",
expectedResult: resource.Result{
Content: "0.003",
},
accountData: map[string]string{
"Amount": "0.003",
},
},
{
name: "Missing amount",
expectedResult: resource.Result{},
accountData: map[string]string{
"Amount": "",
},
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
// Reset the mock state
mockAccountFileHandler.Mock = mock.Mock{}
mockAccountFileHandler.On("ReadAccountData").Return(tt.accountData, nil)
result, err := h.GetAmount(context.Background(), "", nil)
assert.NoError(t, err)
assert.Equal(t, tt.expectedResult.Content, result.Content)
mockAccountFileHandler.AssertCalled(t, "ReadAccountData")
})
}
}

View File

@ -1,44 +0,0 @@
package mocks
import (
"git.grassecon.net/urdt/ussd/internal/models"
"github.com/stretchr/testify/mock"
)
type MockAccountFileHandler struct {
mock.Mock
}
func (m *MockAccountFileHandler) EnsureFileExists() error {
args := m.Called()
return args.Error(0)
}
func (m *MockAccountFileHandler) ReadAccountData() (map[string]string, error) {
args := m.Called()
return args.Get(0).(map[string]string), args.Error(1)
}
func (m *MockAccountFileHandler) WriteAccountData(data map[string]string) error {
args := m.Called(data)
return args.Error(0)
}
type MockAccountService struct {
mock.Mock
}
func (m *MockAccountService) CreateAccount() (*models.AccountResponse, error) {
args := m.Called()
return args.Get(0).(*models.AccountResponse), args.Error(1)
}
func (m *MockAccountService) CheckAccountStatus(TrackingId string) (string, error) {
args := m.Called()
return args.Get(0).(string), args.Error(1)
}
func (m *MockAccountService) CheckBalance(PublicKey string) (string, error) {
args := m.Called()
return args.Get(0).(string), args.Error(1)
}

View File

@ -1,15 +0,0 @@
package models
import (
"encoding/json"
)
type AccountResponse struct {
Ok bool `json:"ok"`
Result struct {
CustodialId json.Number `json:"custodialId"`
PublicKey string `json:"publicKey"`
TrackingId string `json:"trackingId"`
} `json:"result"`
}

View File

@ -1,12 +0,0 @@
package models
import "encoding/json"
type BalanceResponse struct {
Ok bool `json:"ok"`
Result struct {
Balance string `json:"balance"`
Nonce json.Number `json:"nonce"`
} `json:"result"`
}

View File

@ -1,22 +0,0 @@
package models
import "git.defalsify.org/vise.git/state"
const (
USERFLAG_LANGUAGE_SET = iota + state.FLAG_USERSTART
USERFLAG_ACCOUNT_CREATED
USERFLAG_ACCOUNT_PENDING
USERFLAG_ACCOUNT_SUCCESS
USERFLAG_ACCOUNT_AUTHORIZED
USERFLAG_INVALID_RECIPIENT
USERFLAG_INVALID_RECIPIENT_WITH_INVITE
USERFLAG_INCORRECTPIN
USERFLAG_ALLOW_UPDATE
USERFLAG_INVALID_AMOUNT
USERFLAG_PIN_SET
USERFLAG_VALIDPIN
USERFLAG_PINMISMATCH
USERFLAG_INCORRECTDATEFORMAT
USERFLAG_ACCOUNT_CREATION_FAILED
USERFLAG_SINGLE_EDIT
)

View File

@ -1,20 +0,0 @@
package models
import (
"encoding/json"
"time"
)
type TrackStatusResponse struct {
Ok bool `json:"ok"`
Result struct {
Transaction struct {
CreatedAt time.Time `json:"createdAt"`
Status string `json:"status"`
TransferValue json.Number `json:"transferValue"`
TxHash string `json:"txHash"`
TxType string `json:"txType"`
}
} `json:"result"`
}

View File

@ -1,46 +0,0 @@
package utils
import (
"encoding/json"
"os"
)
type AccountFileHandler struct {
FilePath string
}
func NewAccountFileHandler(path string) *AccountFileHandler {
return &AccountFileHandler{FilePath: path}
}
func (afh *AccountFileHandler) ReadAccountData() (map[string]string, error) {
jsonData, err := os.ReadFile(afh.FilePath)
if err != nil {
return nil, err
}
var accountData map[string]string
err = json.Unmarshal(jsonData, &accountData)
if err != nil {
return nil, err
}
return accountData, nil
}
func (afh *AccountFileHandler) WriteAccountData(accountData map[string]string) error {
jsonData, err := json.Marshal(accountData)
if err != nil {
return err
}
return os.WriteFile(afh.FilePath, jsonData, 0644)
}
func (afh *AccountFileHandler) EnsureFileExists() error {
f, err := os.OpenFile(afh.FilePath, os.O_APPEND|os.O_CREATE|os.O_WRONLY, 0644)
if err != nil {
return err
}
return f.Close()
}

View File

@ -1,35 +0,0 @@
package utils
import "time"
// CalculateAge calculates the age based on a given birthdate and the current date in the format dd/mm/yy
// It adjusts for cases where the current date is before the birthday in the current year.
func CalculateAge(birthdate, today time.Time) int {
today = today.In(birthdate.Location())
ty, tm, td := today.Date()
today = time.Date(ty, tm, td, 0, 0, 0, 0, time.UTC)
by, bm, bd := birthdate.Date()
birthdate = time.Date(by, bm, bd, 0, 0, 0, 0, time.UTC)
if today.Before(birthdate) {
return 0
}
age := ty - by
anniversary := birthdate.AddDate(age, 0, 0)
if anniversary.After(today) {
age--
}
return age
}
// CalculateAgeWithYOB calculates the age based on the given year of birth (YOB).
// It subtracts the YOB from the current year to determine the age.
//
// Parameters:
// yob: The year of birth as an integer.
//
// Returns:
// The calculated age as an integer.
func CalculateAgeWithYOB(yob int) int {
currentYear := time.Now().Year()
return currentYear - yob
}

View File

@ -1,13 +0,0 @@
package utils
type AccountFileHandlerInterface interface {
EnsureFileExists() error
ReadAccountData() (map[string]string, error)
WriteAccountData(data map[string]string) error
}

110
request/base.go Normal file
View File

@ -0,0 +1,110 @@
package request
import (
"git.defalsify.org/vise.git/db"
"git.defalsify.org/vise.git/engine"
"git.defalsify.org/vise.git/persist"
"git.defalsify.org/vise.git/resource"
"git.grassecon.net/grassrootseconomics/visedriver/storage"
"git.grassecon.net/grassrootseconomics/visedriver/errors"
"git.grassecon.net/grassrootseconomics/visedriver/entry"
)
type BaseRequestHandler struct {
cfgTemplate engine.Config
rp RequestParser
rs resource.Resource
hn entry.EntryHandler
provider storage.StorageProvider
}
//func NewBaseRequestHandler(cfg engine.Config, rs resource.Resource, stateDb db.Db, userdataDb db.Db, rp request.RequestParser, hn *handlers.Handlers) *BaseRequestHandler {
func NewBaseRequestHandler(cfg engine.Config, rs resource.Resource, stateDb db.Db, userdataDb db.Db, rp RequestParser, hn entry.EntryHandler) *BaseRequestHandler {
return &BaseRequestHandler{
cfgTemplate: cfg,
rs: rs,
hn: hn,
rp: rp,
provider: storage.NewSimpleStorageProvider(stateDb, userdataDb),
}
}
func (f *BaseRequestHandler) Shutdown() {
err := f.provider.Close()
if err != nil {
logg.Errorf("handler shutdown error", "err", err)
}
}
func (f *BaseRequestHandler) GetEngine(cfg engine.Config, rs resource.Resource, pr *persist.Persister) engine.Engine {
en := engine.NewEngine(cfg, rs)
en = en.WithPersister(pr)
return en
}
func(f *BaseRequestHandler) Process(rqs RequestSession) (RequestSession, error) {
var r bool
var err error
var ok bool
logg.InfoCtxf(rqs.Ctx, "new request", "data", rqs)
rqs.Storage, err = f.provider.Get(rqs.Config.SessionId)
if err != nil {
logg.ErrorCtxf(rqs.Ctx, "", "storage get error", err)
return rqs, errors.ErrStorage
}
//f.hn = f.hn.WithPersister(rqs.Storage.Persister)
f.hn.SetPersister(rqs.Storage.Persister)
defer func() {
f.hn.Exit()
}()
eni := f.GetEngine(rqs.Config, f.rs, rqs.Storage.Persister)
en, ok := eni.(*engine.DefaultEngine)
if !ok {
perr := f.provider.Put(rqs.Config.SessionId, rqs.Storage)
rqs.Storage = nil
if perr != nil {
logg.ErrorCtxf(rqs.Ctx, "", "storage put error", perr)
}
return rqs, errors.ErrEngineType
}
en = en.WithFirst(f.hn.Init)
if rqs.Config.EngineDebug {
en = en.WithDebug(nil)
}
rqs.Engine = en
r, err = rqs.Engine.Exec(rqs.Ctx, rqs.Input)
if err != nil {
perr := f.provider.Put(rqs.Config.SessionId, rqs.Storage)
rqs.Storage = nil
if perr != nil {
logg.ErrorCtxf(rqs.Ctx, "", "storage put error", perr)
}
return rqs, err
}
rqs.Continue = r
return rqs, nil
}
func(f *BaseRequestHandler) Output(rqs RequestSession) (RequestSession, error) {
var err error
_, err = rqs.Engine.Flush(rqs.Ctx, rqs.Writer)
return rqs, err
}
func(f *BaseRequestHandler) Reset(rqs RequestSession) (RequestSession, error) {
defer f.provider.Put(rqs.Config.SessionId, rqs.Storage)
return rqs, rqs.Engine.Finish()
}
func (f *BaseRequestHandler) GetConfig() engine.Config {
return f.cfgTemplate
}
func(f *BaseRequestHandler) GetRequestParser() RequestParser {
return f.rp
}

37
request/http/parse.go Normal file
View File

@ -0,0 +1,37 @@
package http
import (
"context"
"io/ioutil"
"net/http"
"git.grassecon.net/grassrootseconomics/visedriver/errors"
)
type DefaultRequestParser struct {
}
func (rp *DefaultRequestParser) GetSessionId(ctx context.Context, rq any) (string, error) {
rqv, ok := rq.(*http.Request)
if !ok {
return "", errors.ErrInvalidRequest
}
v := rqv.Header.Get("X-Vise-Session")
if v == "" {
return "", errors.ErrSessionMissing
}
return v, nil
}
func (rp *DefaultRequestParser) GetInput(rq any) ([]byte, error) {
rqv, ok := rq.(*http.Request)
if !ok {
return nil, errors.ErrInvalidRequest
}
defer rqv.Body.Close()
v, err := ioutil.ReadAll(rqv.Body)
if err != nil {
return nil, err
}
return v, nil
}

92
request/http/server.go Normal file
View File

@ -0,0 +1,92 @@
package http
import (
"net/http"
"strconv"
"git.defalsify.org/vise.git/logging"
"git.grassecon.net/grassrootseconomics/visedriver/request"
"git.grassecon.net/grassrootseconomics/visedriver/errors"
)
var (
logg = logging.NewVanilla().WithDomain("visedriver.http.session")
)
// HTTPRequestHandler implements the session handler for HTTP
type HTTPRequestHandler struct {
request.RequestHandler
}
func (f *HTTPRequestHandler) WriteError(w http.ResponseWriter, code int, err error) {
s := err.Error()
w.Header().Set("Content-Length", strconv.Itoa(len(s)))
w.WriteHeader(code)
_, err = w.Write([]byte(s))
if err != nil {
logg.Errorf("error writing error!!", "err", err, "olderr", s)
w.WriteHeader(500)
}
}
func NewHTTPRequestHandler(h request.RequestHandler) *HTTPRequestHandler {
return &HTTPRequestHandler{
RequestHandler: h,
}
}
func (hh *HTTPRequestHandler) ServeHTTP(w http.ResponseWriter, req *http.Request) {
var code int
var err error
var perr error
rqs := request.RequestSession{
Ctx: req.Context(),
Writer: w,
}
rp := hh.GetRequestParser()
cfg := hh.GetConfig()
cfg.SessionId, err = rp.GetSessionId(req.Context(), req)
if err != nil {
logg.ErrorCtxf(rqs.Ctx, "", "header processing error", err)
hh.WriteError(w, 400, err)
}
rqs.Config = cfg
rqs.Input, err = rp.GetInput(req)
if err != nil {
logg.ErrorCtxf(rqs.Ctx, "", "header processing error", err)
hh.WriteError(w, 400, err)
return
}
rqs, err = hh.Process(rqs)
switch err {
case errors.ErrStorage:
code = 500
case errors.ErrEngineInit:
code = 500
case errors.ErrEngineExec:
code = 500
default:
code = 200
}
if code != 200 {
hh.WriteError(w, 500, err)
return
}
w.WriteHeader(200)
w.Header().Set("Content-Type", "text/plain")
rqs, err = hh.Output(rqs)
rqs, perr = hh.Reset(rqs)
if err != nil {
hh.WriteError(w, 500, err)
return
}
if perr != nil {
hh.WriteError(w, 500, perr)
return
}
}

233
request/http/server_test.go Normal file
View File

@ -0,0 +1,233 @@
package http
import (
"bytes"
"context"
"errors"
"net/http"
"net/http/httptest"
"testing"
"git.defalsify.org/vise.git/engine"
viseerrors "git.grassecon.net/grassrootseconomics/visedriver/errors"
"git.grassecon.net/grassrootseconomics/visedriver/testutil/mocks/httpmocks"
"git.grassecon.net/grassrootseconomics/visedriver/request"
)
// invalidRequestType is a custom type to test invalid request scenarios
type invalidRequestType struct{}
// errorReader is a helper type that always returns an error when Read is called
type errorReader struct{}
func (e *errorReader) Read(p []byte) (n int, err error) {
return 0, errors.New("read error")
}
func TestRequestHandler_ServeHTTP(t *testing.T) {
tests := []struct {
name string
sessionID string
input []byte
parserErr error
processErr error
outputErr error
resetErr error
expectedStatus int
}{
{
name: "Success",
sessionID: "123",
input: []byte("test input"),
expectedStatus: http.StatusOK,
},
{
name: "Missing Session ID",
sessionID: "",
parserErr: viseerrors.ErrSessionMissing,
expectedStatus: http.StatusBadRequest,
},
{
name: "Process Error",
sessionID: "123",
input: []byte("test input"),
processErr: viseerrors.ErrStorage,
expectedStatus: http.StatusInternalServerError,
},
{
name: "Output Error",
sessionID: "123",
input: []byte("test input"),
outputErr: errors.New("output error"),
expectedStatus: http.StatusOK,
},
{
name: "Reset Error",
sessionID: "123",
input: []byte("test input"),
resetErr: errors.New("reset error"),
expectedStatus: http.StatusOK,
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
mockRequestParser := &httpmocks.MockRequestParser{
GetSessionIdFunc: func(any) (string, error) {
return tt.sessionID, tt.parserErr
},
GetInputFunc: func(any) ([]byte, error) {
return tt.input, nil
},
}
mockRequestHandler := &httpmocks.MockRequestHandler{
ProcessFunc: func(rs request.RequestSession) (request.RequestSession, error) {
return rs, tt.processErr
},
OutputFunc: func(rs request.RequestSession) (request.RequestSession, error) {
return rs, tt.outputErr
},
ResetFunc: func(rs request.RequestSession) (request.RequestSession, error) {
return rs, tt.resetErr
},
GetRequestParserFunc: func() request.RequestParser {
return mockRequestParser
},
GetConfigFunc: func() engine.Config {
return engine.Config{}
},
}
sessionHandler := &HTTPRequestHandler{
RequestHandler: mockRequestHandler,
}
req := httptest.NewRequest(http.MethodPost, "/", bytes.NewBuffer(tt.input))
req.Header.Set("X-Vise-Session", tt.sessionID)
rr := httptest.NewRecorder()
sessionHandler.ServeHTTP(rr, req)
if status := rr.Code; status != tt.expectedStatus {
t.Errorf("handler returned wrong status code: got %v want %v",
status, tt.expectedStatus)
}
})
}
}
func TestRequestHandler_WriteError(t *testing.T) {
handler := &HTTPRequestHandler{}
mockWriter := &httpmocks.MockWriter{}
err := errors.New("test error")
handler.WriteError(mockWriter, http.StatusBadRequest, err)
if mockWriter.WrittenString != "" {
t.Errorf("Expected empty body, got %s", mockWriter.WrittenString)
}
}
func TestDefaultRequestParser_GetSessionId(t *testing.T) {
tests := []struct {
name string
request any
expectedID string
expectedError error
}{
{
name: "Valid Session ID",
request: func() *http.Request {
req := httptest.NewRequest(http.MethodPost, "/", nil)
req.Header.Set("X-Vise-Session", "123456")
return req
}(),
expectedID: "123456",
expectedError: nil,
},
{
name: "Missing Session ID",
request: httptest.NewRequest(http.MethodPost, "/", nil),
expectedID: "",
expectedError: viseerrors.ErrSessionMissing,
},
{
name: "Invalid Request Type",
request: invalidRequestType{},
expectedID: "",
expectedError: viseerrors.ErrInvalidRequest,
},
}
parser := &DefaultRequestParser{}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
id, err := parser.GetSessionId(context.Background(),tt.request)
if id != tt.expectedID {
t.Errorf("Expected session ID %s, got %s", tt.expectedID, id)
}
if err != tt.expectedError {
t.Errorf("Expected error %v, got %v", tt.expectedError, err)
}
})
}
}
func TestDefaultRequestParser_GetInput(t *testing.T) {
tests := []struct {
name string
request any
expectedInput []byte
expectedError error
}{
{
name: "Valid Input",
request: func() *http.Request {
return httptest.NewRequest(http.MethodPost, "/", bytes.NewBufferString("test input"))
}(),
expectedInput: []byte("test input"),
expectedError: nil,
},
{
name: "Empty Input",
request: httptest.NewRequest(http.MethodPost, "/", nil),
expectedInput: []byte{},
expectedError: nil,
},
{
name: "Invalid Request Type",
request: invalidRequestType{},
expectedInput: nil,
expectedError: viseerrors.ErrInvalidRequest,
},
{
name: "Read Error",
request: func() *http.Request {
return httptest.NewRequest(http.MethodPost, "/", &errorReader{})
}(),
expectedInput: nil,
expectedError: errors.New("read error"),
},
}
parser := &DefaultRequestParser{}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
input, err := parser.GetInput(tt.request)
if !bytes.Equal(input, tt.expectedInput) {
t.Errorf("Expected input %s, got %s", tt.expectedInput, input)
}
if err != tt.expectedError && (err == nil || err.Error() != tt.expectedError.Error()) {
t.Errorf("Expected error %v, got %v", tt.expectedError, err)
}
})
}
}

42
request/request.go Normal file
View File

@ -0,0 +1,42 @@
package request
import (
"context"
"io"
"git.defalsify.org/vise.git/resource"
"git.defalsify.org/vise.git/persist"
"git.defalsify.org/vise.git/engine"
"git.defalsify.org/vise.git/logging"
"git.grassecon.net/grassrootseconomics/visedriver/storage"
)
var (
logg = logging.NewVanilla().WithDomain("visedriver.request")
)
type RequestSession struct {
Ctx context.Context
Config engine.Config
Engine engine.Engine
Input []byte
Storage *storage.Storage
Writer io.Writer
Continue bool
}
// TODO: seems like can remove this.
type RequestParser interface {
GetSessionId(ctx context.Context, rq any) (string, error)
GetInput(rq any) ([]byte, error)
}
type RequestHandler interface {
GetConfig() engine.Config
GetRequestParser() RequestParser
GetEngine(cfg engine.Config, rs resource.Resource, pe *persist.Persister) engine.Engine
Process(rs RequestSession) (RequestSession, error)
Output(rs RequestSession) (RequestSession, error)
Reset(rs RequestSession) (RequestSession, error)
Shutdown()
}

44
sample_tokens.json Normal file
View File

@ -0,0 +1,44 @@
{
"ok": true,
"description": "Token holdings with current balances",
"result": {
"holdings": [
{
"contractAddress": "0x6CC75A06ac72eB4Db2eE22F781F5D100d8ec03ee",
"tokenSymbol": "FSPTST",
"tokenDecimals": "6",
"balance": "8869964242"
},
{
"contractAddress": "0x724F2910D790B54A39a7638282a45B1D83564fFA",
"tokenSymbol": "GEO",
"tokenDecimals": "6",
"balance": "9884"
},
{
"contractAddress": "0x2105a206B7bec31E2F90acF7385cc8F7F5f9D273",
"tokenSymbol": "MFNK",
"tokenDecimals": "6",
"balance": "19788697"
},
{
"contractAddress": "0x63DE2Ac8D1008351Cc69Fb8aCb94Ba47728a7E83",
"tokenSymbol": "MILO",
"tokenDecimals": "6",
"balance": "75"
},
{
"contractAddress": "0xd4c288865Ce0985a481Eef3be02443dF5E2e4Ea9",
"tokenSymbol": "SOHAIL",
"tokenDecimals": "6",
"balance": "27874115"
},
{
"contractAddress": "0x45d747172e77d55575c197CbA9451bC2CD8F4958",
"tokenSymbol": "SRF",
"tokenDecimals": "6",
"balance": "2745987"
}
]
}
}

View File

@ -1,17 +0,0 @@
# Variables to match files in the current directory
INPUTS = $(wildcard ./*.vis)
TXTS = $(wildcard ./*.txt.orig)
# Rule to build .bin files from .vis files
%.vis:
go run ../../go-vise/dev/asm $(basename $@).vis > $(basename $@).bin
@echo "Built $(basename $@).bin from $(basename $@).vis"
# Rule to copy .orig files to .txt
%.txt.orig:
cp -v $(basename $@).orig $(basename $@)
@echo "Copied $(basename $@).orig to $(basename $@)"
# 'all' target depends on all .vis and .txt.orig files
all: $(INPUTS) $(TXTS)
@echo "Running all: $(INPUTS) $(TXTS)"

View File

@ -1 +0,0 @@
Your account is being created...

View File

@ -1,4 +0,0 @@
RELOAD verify_pin
CATCH create_pin_mismatch 20 1
LOAD quit 0
HALT

View File

@ -1 +0,0 @@
Your account creation request failed. Please try again later.

View File

@ -1,3 +0,0 @@
MOUT quit 9
HALT
INCMP quit 9

View File

@ -1 +0,0 @@
Ombi lako la kusajiliwa haliwezi kukamilishwa. Tafadhali jaribu tena baadaye.

View File

@ -1 +0,0 @@
Akaunti yako inatengenezwa...

View File

@ -1 +0,0 @@
My Account

View File

@ -1 +0,0 @@
Akaunti yangu

View File

@ -1 +0,0 @@
Your account is still being created.

View File

@ -1,3 +0,0 @@
RELOAD check_account_status
CATCH main 11 1
HALT

View File

@ -1 +0,0 @@
Akaunti yako bado inatengenezwa

View File

@ -1 +0,0 @@
Address: {{.check_identifier}}

View File

@ -1,6 +0,0 @@
LOAD check_identifier 0
RELOAD check_identifier
MAP check_identifier
MOUT quit 9
HALT
INCMP quit 9

View File

@ -1,2 +0,0 @@
Maximum amount: {{.max_amount}}
Enter amount:

View File

@ -1,12 +0,0 @@
LOAD reset_transaction_amount 0
LOAD max_amount 10
MAP max_amount
MOUT back 0
HALT
LOAD validate_amount 64
RELOAD validate_amount
CATCH invalid_amount 17 1
INCMP _ 0
LOAD get_recipient 12
LOAD get_sender 64
INCMP transaction_pin *

View File

@ -1,2 +0,0 @@
Kiwango cha juu: {{.max_amount}}
Weka kiwango:

View File

@ -1 +0,0 @@
Back

View File

@ -1 +0,0 @@
Rudi

View File

@ -1 +0,0 @@
Balances:

View File

@ -1,8 +0,0 @@
LOAD reset_unlocked 0
MOUT my_balance 1
MOUT community_balance 2
MOUT back 0
HALT
INCMP _ 0
INCMP my_balance 1
INCMP community_balance 2

View File

@ -1 +0,0 @@
Salio

View File

@ -1 +0,0 @@
Change language

View File

@ -1 +0,0 @@
Badili lugha

View File

@ -1 +0,0 @@
Change PIN

View File

@ -1 +0,0 @@
Badili PIN

View File

@ -1 +0,0 @@
Check balances

View File

@ -1 +0,0 @@
Angalia salio

View File

@ -1 +0,0 @@
Check statement

View File

@ -1 +0,0 @@
Taarifa ya matumizi

View File

@ -1 +0,0 @@
Salio la kikundi

View File

@ -1,2 +0,0 @@
Your community balance is: 0.00SRF

View File

@ -1,5 +0,0 @@
LOAD reset_incorrect 0
CATCH incorrect_pin 15 1
CATCH pin_entry 12 0
LOAD quit_with_balance 0
HALT

View File

@ -1 +0,0 @@
Community balance

View File

@ -1 +0,0 @@
Salio la kikundi

View File

@ -1 +0,0 @@
Enter your four number PIN again:

View File

@ -1,4 +0,0 @@
LOAD save_pin 0
HALT
LOAD verify_pin 8
INCMP account_creation *

View File

@ -1 +0,0 @@
Weka PIN yako tena:

View File

@ -1 +0,0 @@
Please enter a new four number PIN for your account:

View File

@ -1,9 +0,0 @@
LOAD create_account 0
CATCH account_creation_failed 22 1
MOUT exit 0
HALT
LOAD save_pin 0
RELOAD save_pin
CATCH . 15 1
INCMP quit 0
INCMP confirm_create_pin *

View File

@ -1 +0,0 @@
The PIN is not a match. Try again

View File

@ -1,5 +0,0 @@
MOUT retry 1
MOUT quit 9
HALT
INCMP confirm_create_pin 1
INCMP quit 9

View File

@ -1 +0,0 @@
PIN uliyoweka haifanani. Jaribu tena

View File

@ -1 +0,0 @@
Tafadhali weka PIN mpya yenye nambari nne kwa akaunti yako:

View File

@ -1,5 +0,0 @@
Wasifu wangu
Name: Not provided
Gender: Not provided
Age: Not provided
Location: Not provided

View File

@ -1,3 +0,0 @@
MOUT back 0
HALT
INCMP _ 0

View File

@ -1 +0,0 @@
Edit gender

View File

@ -1 +0,0 @@
Weka jinsia

View File

@ -1 +0,0 @@
Edit location

View File

@ -1 +0,0 @@
Weka eneo

View File

@ -1 +0,0 @@
Edit name

View File

@ -1 +0,0 @@
Weka jina

View File

@ -1 +0,0 @@
Edit offerings

View File

@ -1 +0,0 @@
Weka unachouza

View File

@ -1 +0,0 @@
My profile

View File

@ -1,20 +0,0 @@
LOAD reset_account_authorized 16
LOAD reset_allow_update 0
RELOAD reset_allow_update
MOUT edit_name 1
MOUT edit_gender 2
MOUT edit_yob 3
MOUT edit_location 4
MOUT edit_offerings 5
MOUT view 6
MOUT back 0
HALT
INCMP _ 0
LOAD set_reset_single_edit 0
RELOAD set_reset_single_edit
INCMP enter_name 1
INCMP select_gender 2
INCMP enter_yob 3
INCMP enter_location 4
INCMP enter_offerings 5
INCMP view_profile 6

View File

@ -1 +0,0 @@
Wasifu wangu

View File

@ -1 +0,0 @@
Edit year of birth

View File

@ -1 +0,0 @@
Weka mwaka wa kuzaliwa

View File

@ -1 +0,0 @@
Enter family name:

View File

@ -1,5 +0,0 @@
LOAD save_firstname 0
MOUT back 0
HALT
INCMP _ 0
INCMP select_gender *

View File

@ -1 +0,0 @@
Enter your location:

View File

@ -1,12 +0,0 @@
CATCH incorrect_date_format 21 1
LOAD save_yob 0
CATCH update_success 16 1
MOUT back 0
HALT
INCMP _ 0
LOAD save_location 0
CATCH pin_entry 23 1
INCMP enter_offerings *

View File

@ -1 +0,0 @@
Weka eneo:

View File

@ -1 +0,0 @@
Enter your first names:

View File

@ -1,4 +0,0 @@
MOUT back 0
HALT
INCMP _ 0
INCMP enter_familyname *

View File

@ -1 +0,0 @@
Weka majina yako ya kwanza:

View File

@ -1 +0,0 @@
Enter the services or goods you offer:

View File

@ -1,8 +0,0 @@
LOAD save_location 0
CATCH incorrect_pin 15 1
CATCH update_success 16 1
MOUT back 0
HALT
LOAD save_offerings 0
INCMP _ 0
INCMP pin_entry *

Some files were not shown because too many files have changed in this diff Show More