wip-account-creation #4
267
cmd/main.go
@ -27,6 +27,7 @@ const (
|
||||
USERFLAG_INVALID_RECIPIENT
|
||||
USERFLAG_INVALID_RECIPIENT_WITH_INVITE
|
||||
USERFLAG_INCORRECTPIN
|
||||
USERFLAG_UNLOCKFORUPDATE
|
||||
)
|
||||
|
||||
const (
|
||||
@ -70,6 +71,193 @@ type fsData struct {
|
||||
st *state.State
|
||||
}
|
||||
|
||||
func (fsd *fsData) saveFirstName(cxt context.Context, sym string, input []byte) (resource.Result, error) {
|
||||
res := resource.Result{}
|
||||
fp := fsd.path + "_data"
|
||||
|
||||
Alfred-mk marked this conversation as resolved
Outdated
|
||||
jsonData, err := os.ReadFile(fp)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
|
||||
var accountData map[string]string
|
||||
err = json.Unmarshal(jsonData, &accountData)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
if len(input) > 0 {
|
||||
name := string(input)
|
||||
accountData["FirstName"] = name
|
||||
updatedJsonData, err := json.Marshal(accountData)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
|
||||
err = os.WriteFile(fp, updatedJsonData, 0644)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
}
|
||||
|
||||
return res, nil
|
||||
}
|
||||
|
||||
func (fsd *fsData) saveFamilyName(cxt context.Context, sym string, input []byte) (resource.Result, error) {
|
||||
res := resource.Result{}
|
||||
fp := fsd.path + "_data"
|
||||
|
||||
jsonData, err := os.ReadFile(fp)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
|
||||
var accountData map[string]string
|
||||
err = json.Unmarshal(jsonData, &accountData)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
if len(input) > 0 {
|
||||
//Save name
|
||||
secondname := string(input)
|
||||
fmt.Println("FamilyName:", secondname)
|
||||
accountData["FamilyName"] = secondname
|
||||
updatedJsonData, err := json.Marshal(accountData)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
|
||||
err = os.WriteFile(fp, updatedJsonData, 0644)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
}
|
||||
|
||||
return res, nil
|
||||
}
|
||||
func (fsd *fsData) saveYOB(cxt context.Context, sym string, input []byte) (resource.Result, error) {
|
||||
res := resource.Result{}
|
||||
fp := fsd.path + "_data"
|
||||
jsonData, err := os.ReadFile(fp)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
var accountData map[string]string
|
||||
err = json.Unmarshal(jsonData, &accountData)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
if len(input) > 0 {
|
||||
yob := string(input)
|
||||
fmt.Println("YOB", yob)
|
||||
accountData["YOB"] = yob
|
||||
updatedJsonData, err := json.Marshal(accountData)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
|
||||
Alfred-mk marked this conversation as resolved
Outdated
lash
commented
This code is repeated many times. Could we please abstract the json fs part of the get and set to a module implementing an interface with This code is repeated many times. Could we please abstract the json fs part of the get and set to a module implementing an interface with `Get` and `Put`?
|
||||
err = os.WriteFile(fp, updatedJsonData, 0644)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
}
|
||||
|
||||
return res, nil
|
||||
}
|
||||
|
||||
func (fsd *fsData) saveLocation(cxt context.Context, sym string, input []byte) (resource.Result, error) {
|
||||
res := resource.Result{}
|
||||
Alfred-mk marked this conversation as resolved
Outdated
lash
commented
perhaps check this input, 2 or 4 digits, numeric perhaps check this input, 2 or 4 digits, numeric
lash
commented
priority **priority**
|
||||
fp := fsd.path + "_data"
|
||||
jsonData, err := os.ReadFile(fp)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
var accountData map[string]string
|
||||
err = json.Unmarshal(jsonData, &accountData)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
if len(input) > 0 {
|
||||
location := string(input)
|
||||
fmt.Println("Location:", location)
|
||||
accountData["Location"] = location
|
||||
updatedJsonData, err := json.Marshal(accountData)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
|
||||
err = os.WriteFile(fp, updatedJsonData, 0644)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return res, nil
|
||||
}
|
||||
|
||||
func (fsd *fsData) saveGender(ctx context.Context, sym string, input []byte) (resource.Result, error) {
|
||||
res := resource.Result{}
|
||||
fp := fsd.path + "_data"
|
||||
jsonData, err := os.ReadFile(fp)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
var accountData map[string]string
|
||||
err = json.Unmarshal(jsonData, &accountData)
|
||||
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 = "Other"
|
||||
}
|
||||
fmt.Println("gender", gender)
|
||||
accountData["Gender"] = gender
|
||||
updatedJsonData, err := json.Marshal(accountData)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
|
||||
err = os.WriteFile(fp, updatedJsonData, 0644)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
}
|
||||
return res, nil
|
||||
}
|
||||
|
||||
func (fsd *fsData) saveOfferings(ctx context.Context, sym string, input []byte) (resource.Result, error) {
|
||||
res := resource.Result{}
|
||||
Alfred-mk marked this conversation as resolved
Outdated
lash
commented
is this a choice in the current ussd? is this a choice in the current ussd?
Alfred-mk
commented
Yes, the current USSD has the option of updating the gender, and the options are Male, Female and Other Yes, the current USSD has the option of updating the gender, and the options are Male, Female and Other
|
||||
fp := fsd.path + "_data"
|
||||
jsonData, err := os.ReadFile(fp)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
var accountData map[string]string
|
||||
err = json.Unmarshal(jsonData, &accountData)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
if len(input) > 0 {
|
||||
offerings := string(input)
|
||||
fmt.Println("Offerings:", offerings)
|
||||
accountData["Offerings"] = offerings
|
||||
updatedJsonData, err := json.Marshal(accountData)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
err = os.WriteFile(fp, updatedJsonData, 0644)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
}
|
||||
return res, nil
|
||||
}
|
||||
|
||||
func (fsd *fsData) SetLanguageSelected(ctx context.Context, sym string, input []byte) (resource.Result, error) {
|
||||
inputStr := string(input)
|
||||
res := resource.Result{}
|
||||
@ -97,7 +285,18 @@ func (fsd *fsData) create_account(ctx context.Context, sym string, input []byte)
|
||||
}
|
||||
f.Close()
|
||||
|
||||
Alfred-mk marked this conversation as resolved
Outdated
lash
commented
should error? should error?
lash
commented
priority **priority**
Alfred-mk
commented
The switch only takes in two options, 0 or 1. The switch only takes in two options, 0 or 1.
The menu remains on the select language node if an alternative input is provided
|
||||
accountResp, err := createAccount()
|
||||
//accountResp, err := createAccount()
|
||||
accountResp := accountResponse{
|
||||
Ok: true,
|
||||
Result: struct {
|
||||
CustodialId json.Number `json:"custodialId"`
|
||||
PublicKey string `json:"publicKey"`
|
||||
TrackingId string `json:"trackingId"`
|
||||
}{
|
||||
CustodialId: "636",
|
||||
PublicKey: "0x8d86F9D4A4eae41Dc3B68034895EA97BcA90e8c1",
|
||||
TrackingId: "45c67314-7995-4890-89d6-e5af987754ac",
|
||||
}}
|
||||
|
||||
if err != nil {
|
||||
fmt.Println("Failed to create account:", err)
|
||||
@ -124,6 +323,21 @@ func (fsd *fsData) create_account(ctx context.Context, sym string, input []byte)
|
||||
return res, err
|
||||
}
|
||||
|
||||
func (fsd *fsData) resetUnlockForUpdate(ctx context.Context, sym string, input []byte) (resource.Result, error) {
|
||||
res := resource.Result{}
|
||||
res.FlagReset = append(res.FlagReset, USERFLAG_UNLOCKFORUPDATE)
|
||||
return res, nil
|
||||
}
|
||||
|
||||
func (fsd *fsData) resetAccountUnlocked(ctx context.Context,sym string,input []byte) (resource.Result,error){
|
||||
res := resource.Result{}
|
||||
st := fsd.st
|
||||
isSet := st.MatchFlag(USERFLAG_ACCOUNT_UNLOCKED,true)
|
||||
res.FlagReset = append(res.FlagReset, USERFLAG_ACCOUNT_UNLOCKED)
|
||||
fmt.Println("ISSET:",isSet)
|
||||
return res,nil
|
||||
}
|
||||
|
||||
func (fsd *fsData) checkIdentifier(ctx context.Context, sym string, input []byte) (resource.Result, error) {
|
||||
res := resource.Result{}
|
||||
fp := fsd.path + "_data"
|
||||
@ -154,9 +368,11 @@ func (fsd *fsData) unLock(ctx context.Context, sym string, input []byte) (resour
|
||||
return res, nil
|
||||
}
|
||||
if fsd.st.MatchFlag(USERFLAG_ACCOUNT_UNLOCKED, false) {
|
||||
//res.FlagSet = append(res.FlagSet, USERFLAG_UNLOCKFORUPDATE)
|
||||
res.FlagSet = append(res.FlagSet, USERFLAG_ACCOUNT_UNLOCKED)
|
||||
} else {
|
||||
res.FlagReset = append(res.FlagReset, USERFLAG_ACCOUNT_UNLOCKED)
|
||||
//res.FlagReset = append(res.FlagReset, USERFLAG_UNLOCKFORUPDATE)
|
||||
}
|
||||
}
|
||||
return res, nil
|
||||
@ -173,6 +389,11 @@ func (fsd *fsData) ResetIncorrectPin(ctx context.Context, sym string, input []by
|
||||
return res, nil
|
||||
}
|
||||
|
||||
func (fsd *fsData) ShowUpdateSuccess(ctx context.Context, sym string, input []byte) (resource.Result, error) {
|
||||
res := resource.Result{}
|
||||
return res, nil
|
||||
}
|
||||
|
||||
func (fsd *fsData) check_account_status(ctx context.Context, sym string, input []byte) (resource.Result, error) {
|
||||
res := resource.Result{}
|
||||
fp := fsd.path + "_data"
|
||||
@ -197,7 +418,7 @@ func (fsd *fsData) check_account_status(ctx context.Context, sym string, input [
|
||||
|
||||
accountData["Status"] = status
|
||||
|
||||
if status == "SUCCESS" {
|
||||
if status == "REVERTED" {
|
||||
res.FlagSet = append(res.FlagSet, USERFLAG_ACCOUNT_SUCCESS)
|
||||
res.FlagReset = append(res.FlagReset, USERFLAG_ACCOUNT_PENDING)
|
||||
} else {
|
||||
@ -456,6 +677,35 @@ func (fsd *fsData) get_recipient(ctx context.Context, sym string, input []byte)
|
||||
return res, nil
|
||||
}
|
||||
|
||||
|
||||
func (fsd *fsData) getProfileInfo(ctx context.Context,sym string,input []byte) (resource.Result,error){
|
||||
res := resource.Result{}
|
||||
fp := fsd.path + "_data"
|
||||
|
||||
jsonData, err := os.ReadFile(fp)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
|
||||
var accountData map[string]string
|
||||
err = json.Unmarshal(jsonData, &accountData)
|
||||
if err != nil {
|
||||
return res, err
|
||||
}
|
||||
name := accountData["FirstName"]
|
||||
gender := accountData["Gender"]
|
||||
age := accountData["YOB"]
|
||||
location := accountData["Location"]
|
||||
|
||||
// Format the data into a string
|
||||
formattedData := fmt.Sprintf("Name: %s\nGender: %s\nAge: %s\nLocation: %s\n", name, gender, age, location)
|
||||
|
||||
|
||||
res.Content = formattedData
|
||||
|
||||
return res,nil
|
||||
}
|
||||
|
||||
func (fsd *fsData) get_sender(ctx context.Context, sym string, input []byte) (resource.Result, error) {
|
||||
res := resource.Result{}
|
||||
fp := fsd.path + "_data"
|
||||
Alfred-mk marked this conversation as resolved
Outdated
lash
commented
Since the balance is already available, should check that input is not more than balance. Since the balance is already available, should check that input is not more than balance.
lash
commented
priority **priority**
|
||||
@ -585,7 +835,20 @@ func main() {
|
||||
rfs.AddLocalFunc("get_recipient", fs.get_recipient)
|
||||
rfs.AddLocalFunc("get_sender", fs.get_sender)
|
||||
rfs.AddLocalFunc("reset_incorrect", fs.ResetIncorrectPin)
|
||||
rfs.AddLocalFunc("save_firstname", fs.saveFirstName)
|
||||
rfs.AddLocalFunc("save_familyname", fs.saveFamilyName)
|
||||
rfs.AddLocalFunc("save_gender", fs.saveGender)
|
||||
rfs.AddLocalFunc("save_location", fs.saveLocation)
|
||||
rfs.AddLocalFunc("save_yob", fs.saveYOB)
|
||||
rfs.AddLocalFunc("save_offerings", fs.saveOfferings)
|
||||
rfs.AddLocalFunc("quit_with_balance", fs.quitWithBalance)
|
||||
rfs.AddLocalFunc("show_update_success", fs.ShowUpdateSuccess)
|
||||
rfs.AddLocalFunc("reset_unlocked",fs.resetAccountUnlocked)
|
||||
Alfred-mk marked this conversation as resolved
Outdated
lash
commented
The page says four digit PIN, so the input must be checked here. The page says four digit PIN, so the input must be checked here.
lash
commented
priority **priority**
|
||||
rfs.AddLocalFunc("reset_unlock_for_update", fs.resetUnlockForUpdate)
|
||||
rfs.AddLocalFunc("get_profile_info",fs.getProfileInfo)
|
||||
|
||||
|
||||
|
||||
|
||||
cont, err := en.Init(ctx)
|
||||
en.SetDebugger(engine.NewSimpleDebug(nil))
|
||||
|
@ -1,3 +1,4 @@
|
||||
LOAD reset_unlocked 0
|
||||
MOUT my_balance 1
|
||||
MOUT community_balance 2
|
||||
MOUT back 0
|
||||
|
@ -1,3 +1,5 @@
|
||||
LOAD reset_unlocked 0
|
||||
LOAD get_profile_info 0
|
||||
MOUT edit_name 1
|
||||
MOUT edit_gender 2
|
||||
MOUT edit_yob 3
|
||||
|
1
services/registration/enter_familyname
Normal file
@ -0,0 +1 @@
|
||||
Enter family name:
|
6
services/registration/enter_familyname.vis
Normal file
@ -0,0 +1,6 @@
|
||||
LOAD save_firstname 0
|
||||
MOUT back 0
|
||||
HALT
|
||||
INCMP _ 0
|
||||
INCMP select_gender *
|
||||
lash
commented
See https://git.grassecon.net/urdt/ussd/pulls/4/files#issuecomment-1194 No matter where you start in the menu, you always go ahead to the end. Again, if this is how current USSD behaves, we can keep this for now. But we should add a nice-to-have task to change that behavior to only edit full profile when not already edited. See https://git.grassecon.net/urdt/ussd/pulls/4/files#issuecomment-1194
No matter where you start in the menu, you always go ahead to the end.
Again, if this is how current USSD behaves, we can keep this for now. But we should add a nice-to-have task to change that behavior to only edit full profile when not already edited.
|
||||
|
0
services/registration/enter_familyname_swa
Normal file
@ -1,3 +1,5 @@
|
||||
LOAD save_yob 0
|
||||
MOUT back 0
|
||||
HALT
|
||||
INCMP _ 0
|
||||
INCMP enter_offerings *
|
||||
|
@ -1,3 +1,4 @@
|
||||
MOUT back 0
|
||||
HALT
|
||||
INCMP _ 0
|
||||
INCMP enter_familyname *
|
||||
lash
commented
Is this how it works on the USSD now? This has you fill out the entire profile at once. Is this how it works on the USSD now? This has you fill out the entire profile at once.
|
||||
|
@ -1,3 +1,10 @@
|
||||
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 *
|
||||
|
||||
|
||||
|
@ -1,3 +1,5 @@
|
||||
LOAD save_gender 0
|
||||
MOUT back 0
|
||||
HALT
|
||||
INCMP _ 0
|
||||
INCMP enter_location *
|
||||
|
@ -1,3 +1,4 @@
|
||||
LOAD reset_unlock_for_update 0
|
||||
MOUT profile 1
|
||||
MOUT change_language 2
|
||||
MOUT check_balance 3
|
||||
|
@ -1,6 +1,10 @@
|
||||
LOAD save_familyname 0
|
||||
MOUT male 1
|
||||
MOUT female 2
|
||||
MOUT other_gender 3
|
||||
MOUT back 0
|
||||
HALT
|
||||
INCMP _ 0
|
||||
INCMP enter_yob 1
|
||||
INCMP enter_yob 2
|
||||
INCMP enter_yob 3
|
||||
|
1
services/registration/update_success
Normal file
@ -0,0 +1 @@
|
||||
Profile updated successfully
|
3
services/registration/update_success.vis
Normal file
@ -0,0 +1,3 @@
|
||||
MOUT back 0
|
||||
HALT
|
||||
INCMP ^ 0
|
1
services/registration/update_success_swa
Normal file
@ -0,0 +1 @@
|
||||
Akaunti imeupdatiwa
|
2
services/registration/view_profile
Normal file
@ -0,0 +1,2 @@
|
||||
My profile:
|
||||
{{.get_profile_info}}
|
@ -1 +1,8 @@
|
||||
LOAD get_profile_info 0
|
||||
MAP get_profile_info
|
||||
LOAD reset_incorrect 0
|
||||
CATCH incorrect_pin 15 1
|
||||
CATCH pin_entry 12 0
|
||||
MOUT back 0
|
||||
HALT
|
||||
INCMP _ 0
|
||||
|
1
services/registration/view_profile_swa
Normal file
@ -0,0 +1 @@
|
||||
Wasifu wangu
|
can this (and all its methods) be moved to a separate package please?