diff --git a/subjects/atm-management-system/README.md b/subjects/atm-management-system/README.md new file mode 100644 index 00000000..8b72b657 --- /dev/null +++ b/subjects/atm-management-system/README.md @@ -0,0 +1,133 @@ +## ATM + +### Objective + +The objective for this project is to show that you have acquired programming logic and that you are able to adapt to new languages. + +The programming language you are about to use is [C](https://en.wikipedia.org/wiki/C_%28programming_language%29). It will not be asked to create +a project from scratch, insted you will have **to add features or fix the code of a given application**. + +### Instructions + +You will be provided with an ATM management system where users can do the following actions: + +- Login/Register +- Create a new account +- Check the details of existing accounts +- Update information of existing accounts +- Remove existing accounts +- Check list of owned accounts +- Make transactions + +> The application provided will just handle the **login**, the **creation of new accounts** and **checking the list of owned accounts**. The rest of the features must +be implemented by yourself. + +### File System + +A folder which you can find [here](https://downgit.github.io/#/home?url=https://github.com/01-edu/public/tree/master/subjects/atm-management-system/atm-system/) is provided, this folder will have the following `fs`(file system): + +```console +. +| +├── data +│   ├── records.txt +│   └── users.txt +├── Makefile +├── README.md +└── src +    ├── auth.c +    ├── header.h +    ├── main.c +    └── system.c +``` + +The `data` folder presented above will contain information about the users and their accounts: + +- `users.txt` will be the a file that stores all information about each user +- `records.txt` will be the a file that stores all information relevant to the accounts for each user + +The format for the content saved in the file will be displayed like this : + +`users.txt` (name, password): + +```console +Alice 1234password +Michel password1234 +.... +``` + +`records.txt` (user name, account id, date of creation, country, phone nº, type of account) : + +```console +Alice 0 10/02/2020 german 986134231 11090830.00 current +Michel 2 10/10/2021 portugal 914134431 1920.42 savings +Alice 1 10/10/2000 finland 986134231 1234.21 savings +.... +``` + +### Features + +The following features must be implemented by yourself. + +1. The **Registration** feature, you must be able to register new users, users with the same name can not exist (names must be unique). They must be saved in the right file. + +2. The **Update information of existing account** feature, users must be able to update their country or phone number. + + 2.1. You must ask users to input the account `id` they want to change, followed by a prompt asking which field they want to also change (the only fields that are permitted to update is the phone number and the country). + + 2.2. Whenever users update an account, it must be saved into the corresponding file. + +3. The **Checking the details of existing accounts** feature, users must be able to check just one account at a time. + + 3.1. For this it must be asked to input the account id they want to see + + 3.2. If the account is either `savings`, `fixed01`, `fixed02` and `fixed03` the system will display + the information of that account and the interest you will acquire depending on the account: + + - savings: interest rate 0.07% + - fixed01(1 year account): interest rate 0.04% + - fixed02(2 year account): interest rate 0.05% + - fixed03(3 year account): interest rate 0.08% + - If the account is current you must display `You will not get interests because the account is of type current` + +4. The **Make transaction** feature, users must be able to create transactions, withdrawing or depositing money to a certain account. All transactions + must be updated and saved into the corresponding file. + +5. The **Remove existing account** feature, users must be able to delete their own account, the same must happen here, updates must be saved into the corresponding file. + +6. The **Transfer owner** feature, users can transfer their account to another user, by: + + 6.1. Identifying the account and the user they want to transfer the ownership to + + 6.2. Saving the information in the corresponding file + +### Bonus + +As bonus you can add a verification to the field **Transfer owner**. Every time a user transfers ownership of an account the other user who received the account +can be alerted that he or she received an account from someone instantly. +Example: if you have two terminals opened logged with two different users, and one send the account to the other user, +the user who received the account should be instantly notified. +One of the ways of doing this is by using pipes and child processes (communication between processes). + +You can also do more bonus features or update the terminal interface: + +- Better terminal interface (TUI) +- Encryption of passwords +- Adding your own Makefile + +### Example + +You can find an example of the final application [here](https://www.youtube.com/watch?v=xVtikDcGG2E). Do not forget that you are free to +implement whichever kind of interface you desire. It just needs to obey the instructions given above so it can pass the audit. + +This project will help you learn about: + +- [C](https://en.wikipedia.org/wiki/C_%28programming_language%29) language + - Language Fundamentals +- Data manipulation + - File manipulation + - Data structures +- Makefile +- Terminal UI +- Memory management +- Pipes and child processes diff --git a/subjects/atm-management-system/atm_system/Makefile b/subjects/atm-management-system/atm_system/Makefile new file mode 100644 index 00000000..62befd2c --- /dev/null +++ b/subjects/atm-management-system/atm_system/Makefile @@ -0,0 +1,16 @@ +objects = src/main.o src/system.o src/auth.o + +atm : $(objects) + cc -o atm $(objects) + +main.o : src/header.h +kbd.o : src/header.h +command.o : src/header.h +display.o : src/header.h +insert.o : src/header.h +search.o : src/header.h +files.o : src/header.h +utils.o : src/header.h + +clean : + rm -f $(objects) diff --git a/subjects/atm-management-system/atm_system/data/records.txt b/subjects/atm-management-system/atm_system/data/records.txt new file mode 100644 index 00000000..b9d75f71 --- /dev/null +++ b/subjects/atm-management-system/atm_system/data/records.txt @@ -0,0 +1,6 @@ +Alice 0 10/10/2012 Africa 291321234 22432.52 saving + +Michel 2 2/5/2001 Portugal 123543455 10023.230000 fixed01 + +Michel 123 10/10/2020 UK 1234123 12345.30 saving + diff --git a/subjects/atm-management-system/atm_system/data/users.txt b/subjects/atm-management-system/atm_system/data/users.txt new file mode 100644 index 00000000..00694cf8 --- /dev/null +++ b/subjects/atm-management-system/atm_system/data/users.txt @@ -0,0 +1,2 @@ +Alice q1w2e3r4t5y6 +Michel q1w2e3r4t5y6 diff --git a/subjects/atm-management-system/atm_system/src/auth.c b/subjects/atm-management-system/atm_system/src/auth.c new file mode 100644 index 00000000..c3e61b08 --- /dev/null +++ b/subjects/atm-management-system/atm_system/src/auth.c @@ -0,0 +1,59 @@ +#include +#include "header.h" + +char *USERS = "./data/users.txt"; + +void loginMenu(char a[50], char pass[50]) +{ + struct termios oflags, nflags; + + system("clear"); + printf("\n\n\n\t\t\t\t Bank Management System\n\t\t\t\t\t User Login:"); + scanf("%s", a); + + // disabling echo + tcgetattr(fileno(stdin), &oflags); + nflags = oflags; + nflags.c_lflag &= ~ECHO; + nflags.c_lflag |= ECHONL; + + if (tcsetattr(fileno(stdin), TCSANOW, &nflags) != 0) + { + perror("tcsetattr"); + return exit(1); + } + printf("\n\n\n\n\n\t\t\t\tEnter the password to login:"); + scanf("%s", pass); + + // restore terminal + if (tcsetattr(fileno(stdin), TCSANOW, &oflags) != 0) + { + perror("tcsetattr"); + return exit(1); + } +}; + +const char *getPassword(struct User u) +{ + FILE *fp; + struct User userChecker; + + if ((fp = fopen("./data/users.txt", "r")) == NULL) + { + printf("Error! opening file"); + exit(1); + } + + while (fscanf(fp, "%s %s", userChecker.name, userChecker.password) != EOF) + { + if (strcmp(userChecker.name, u.name) == 0) + { + fclose(fp); + char *buff = userChecker.password; + return buff; + } + } + + fclose(fp); + return "no user found"; +} \ No newline at end of file diff --git a/subjects/atm-management-system/atm_system/src/header.h b/subjects/atm-management-system/atm_system/src/header.h new file mode 100644 index 00000000..61d7971a --- /dev/null +++ b/subjects/atm-management-system/atm_system/src/header.h @@ -0,0 +1,37 @@ +#include +#include +#include + +struct Date +{ + int month, day, year; +}; + +// all fields for each record of an account +struct Record +{ + char name[100]; + char country[100]; + int phone; + char accountType[10]; + int accountNbr; + double amount; + struct Date deposit; + struct Date withdraw; +}; + +struct User +{ + char name[50]; + char password[50]; +}; + +// authentication functions +void loginMenu(char a[50], char pass[50]); +void registerMenu(char a[50], char pass[50]); +const char *getPassword(struct User u); + +// system function +void createNewAcc(struct User u); +void mainMenu(struct User u); +void checkAllAccounts(struct User u); diff --git a/subjects/atm-management-system/atm_system/src/main.c b/subjects/atm-management-system/atm_system/src/main.c new file mode 100644 index 00000000..9829a876 --- /dev/null +++ b/subjects/atm-management-system/atm_system/src/main.c @@ -0,0 +1,104 @@ +#include "header.h" + +void mainMenu(struct User u) +{ + int option; + system("clear"); + printf("\n\n\t\t======= ATM =======\n\n"); + printf("\n\t\t-->> Feel free to choose one of the options below <<--\n"); + printf("\n\t\t[1]- Create a new account\n"); + printf("\n\t\t[2]- Update information of account\n"); + printf("\n\t\t[3]- Check accounts\n"); + printf("\n\t\t[4]- Check list of owned account\n"); + printf("\n\t\t[5]- Make Transaction\n"); + printf("\n\t\t[6]- Remove existing account\n"); + printf("\n\t\t[7]- Transfer ownership\n"); + printf("\n\t\t[8]- Exit\n"); + scanf("%d", &option); + + switch (option) + { + case 1: + createNewAcc(u); + break; + case 2: + // student TODO : add your **Update information of existing account** function + // here + break; + case 3: + // student TODO : add your **Check the details of existing accounts** function + // here + break; + case 4: + checkAllAccounts(u); + break; + case 5: + // student TODO : add your **Make transaction** function + // here + break; + case 6: + // student TODO : add your **Remove existing account** function + // here + break; + case 7: + // student TODO : add your **Transfer owner** function + // here + break; + case 8: + exit(1); + break; + default: + printf("Invalid operation!\n"); + } +}; + +void initMenu(struct User *u) +{ + int r = 0; + int option; + system("clear"); + printf("\n\n\t\t======= ATM =======\n"); + printf("\n\t\t-->> Feel free to login / register :\n"); + printf("\n\t\t[1]- login\n"); + printf("\n\t\t[2]- register\n"); + printf("\n\t\t[3]- exit\n"); + while (!r) + { + scanf("%d", &option); + switch (option) + { + case 1: + loginMenu(u->name, u->password); + if (strcmp(u->password, getPassword(*u)) == 0) + { + printf("\n\nPassword Match!"); + } + else + { + printf("\nWrong password!! or User Name\n"); + exit(1); + } + r = 1; + break; + case 2: + // student TODO : add your **Registration** function + // here + r = 1; + break; + case 3: + exit(1); + break; + default: + printf("Insert a valid operation!\n"); + } + } +}; + +int main() +{ + struct User u; + + initMenu(&u); + mainMenu(u); + return 0; +} diff --git a/subjects/atm-management-system/atm_system/src/system.c b/subjects/atm-management-system/atm_system/src/system.c new file mode 100644 index 00000000..1a5f03c9 --- /dev/null +++ b/subjects/atm-management-system/atm_system/src/system.c @@ -0,0 +1,161 @@ +#include "header.h" + +const char *RECORDS = "./data/records.txt"; + +int getAccountFromFile(FILE *ptr, char name[50], struct Record *r) +{ + return fscanf(ptr, "%s %d %d/%d/%d %s %d %lf %s", + name, + &r->accountNbr, + &r->deposit.month, + &r->deposit.day, + &r->deposit.year, + r->country, + &r->phone, + &r->amount, + r->accountType) != EOF; +} + +void saveAccountToFile(FILE *ptr, char name[50], struct Record r) +{ + fprintf(ptr, "%s %d %d/%d/%d %s %d %.2lf %s\n\n", + name, + r.accountNbr, + r.deposit.month, + r.deposit.day, + r.deposit.year, + r.country, + r.phone, + r.amount, + r.accountType); +} + +void stayOrReturn(int notGood, void f(struct User u), struct User u) +{ + int option; + if (notGood == 0) + { + system("clear"); + printf("\n✖ Record not found!!\n"); + invalid: + printf("\nEnter 0 to try again, 1 to return to main menu and 2 to exit:"); + scanf("%d", &option); + if (option == 0) + f(u); + else if (option == 1) + mainMenu(u); + else if (option == 2) + exit(0); + else + { + printf("Insert a valid operation!\n"); + goto invalid; + } + } + else + { + printf("\nEnter 1 to go to the main menu and 0 to exit:"); + scanf("%d", &option); + } + if (option == 1) + { + system("clear"); + mainMenu(u); + } + else + { + system("clear"); + exit(1); + } +} + +void success(struct User u) +{ + int option; + printf("\n✔ Success!\n\n"); +invalid: + printf("Enter 1 to go to the main menu and 0 to exit!\n"); + scanf("%d", &option); + system("clear"); + if (option == 1) + { + mainMenu(u); + } + else if (option == 0) + { + exit(1); + } + else + { + printf("Insert a valid operation!\n"); + goto invalid; + } +} + +void createNewAcc(struct User u) +{ + struct Record r; + struct Record cr; + char userName[50]; + FILE *pf = fopen(RECORDS, "a+"); + +noAccount: + system("clear"); + printf("\t\t\t===== New record =====\n"); + + printf("\nEnter today's date(mm/dd/yyyy):"); + scanf("%d/%d/%d", &r.deposit.month, &r.deposit.day, &r.deposit.year); + printf("\nEnter the account number:"); + scanf("%d", &r.accountNbr); + + while (getAccountFromFile(pf, userName, &cr)) + { + if (strcmp(userName, u.name) == 0 && cr.accountNbr == r.accountNbr) + { + printf("✖ This Account already exists for this user\n\n"); + goto noAccount; + } + } + printf("\nEnter the country:"); + scanf("%s", r.country); + printf("\nEnter the phone number:"); + scanf("%d", &r.phone); + printf("\nEnter amount to deposit: $"); + scanf("%lf", &r.amount); + printf("\nChoose the type of account:\n\t-> saving\n\t-> current\n\t-> fixed01(for 1 year)\n\t-> fixed02(for 2 years)\n\t-> fixed03(for 3 years)\n\n\tEnter your choice:"); + scanf("%s", r.accountType); + + saveAccountToFile(pf, u.name, r); + + fclose(pf); + success(u); +} + +void checkAllAccounts(struct User u) +{ + char userName[100]; + struct Record r; + + FILE *pf = fopen(RECORDS, "r"); + + system("clear"); + printf("\t\t====== All accounts from user, %s =====\n\n", u.name); + while (getAccountFromFile(pf, userName, &r)) + { + if (strcmp(userName, u.name) == 0) + { + printf("_____________________\n"); + printf("\nAccount number:%d\nDeposit Date:%d/%d/%d \ncountry:%s \nPhone number:%d \nAmount deposited: $%.2f \nType Of Account:%s\n", + r.accountNbr, + r.deposit.day, + r.deposit.month, + r.deposit.year, + r.country, + r.phone, + r.amount, + r.accountType); + } + } + fclose(pf); + success(u); +} diff --git a/subjects/atm-management-system/audit/README.md b/subjects/atm-management-system/audit/README.md new file mode 100644 index 00000000..db5ebf7e --- /dev/null +++ b/subjects/atm-management-system/audit/README.md @@ -0,0 +1,95 @@ +#### Functional + +##### Open the application and register a new user with the name `"Alice"` and the password `"q1w2e3r4t5y6"` + +###### Is this user saved in the file `"./data/users.txt"`, and if so are all credentials correct (name and password)? + +##### Open the application and register again the user `"Alice"`. + +###### Did it displayed an error message saying that this user already exists? + +##### Open the file `"./data/users.txt"`. + +###### Are all the user names unique? (ex: no repetition on the name Alice) + +##### Try and login as `"Alice"`. + +###### Was Alice able to enter the main menu? + +##### Try to create two accounts using the user Alice, then select the option `"Update information of account"` and select an account number that does not exist for Alice. + +###### Did the application displayed some kind of error message saying that this account does not exist? + +##### Resorting to the user Alice try and select the option `"Update information of account"` and select one of the accounts you created for Alice. + +###### Did the the application prompt a choice of updating the **phone number** or the **country**? + +##### Resorting to the user Alice try and select the option `"Update information of account"` and select one of the accounts you created for Alice. Then update the phone number of that account. + +###### Was the phone number of that account updated in the application and the file `"records.txt"`? + +##### Resorting to the user Alice try and select the option `"Update information of account"` and select one of the accounts you created for Alice. Then update the country of that account. + +###### Was the country of that account updated in the application and the file `"records.txt"`? + +##### Resorting to the user Alice try to create a new account with: date `"10/10/2012"` account number `"834213"`, country `"UK"`, phone number `"291231392"`, deposit amount $`"1001.20"`, type of account `"saving"`. Then select `"Check accounts"` choose the account you just created. + +###### Did the application displayed the account information and the gain of $5.84 of interest on day 10 of every moth? + +##### Resorting to the user Alice create again an account but with account number "320421" and type of account "fixed01" with the rest of the information as in the last account . Then select `"Check accounts"` and choose the account you just created. + +###### Did the application displayed the account information and the gain of $40.05 of interest on 10/10/2013? + +##### Resorting to the user Alice create again an account but with account number `"3214"` and type of account `"fixed02"` with the rest of the information as in the last account. Then select `"Check accounts"` and choose the account you just created. + +###### Did the application displayed the account information and the gain of $100.12 of interest on 10/10/2014? + +##### Resorting to the user Alice create again an account but with account number `"3212"` and type of account `"fixed03"` with the rest of the information as in the last account. Then select `"Check accounts"` and choose the account you just created. + +###### Did the application displayed the account information and the gain of $240.29 of interest on 10/10/2015? + +##### Resorting to the user Alice select the option `"Make transaction"`. Then choose the account with the id `"3212"` + +###### Are you able to choose between withdrawing or depositing? + +##### Resorting to the user Alice select the option `"Make transaction"`, choose the account with the id `"3212"`. Then try to withdraw money. + +###### Are you able to withdraw money? + +###### And if so, was the withdraw updated in the file `"records.txt"`? + +###### Is it not possible to withdraw an amount superior to your available balance? + +##### Try to deposit money into the account `"3212"`. + +###### Were you able to deposit money into this account? + +###### And if so did it update the file `"records.txt"`? + +##### Resorting to the user Alice try to select the option `"Remove existing account"` and remove the accounts `"834213"`, `"320421"` and `"3214"`. + +###### Can you confirm that those account were deleted, both in the application and file `"records.txt"`? + +##### Resorting to the user Alice select the option `"Remove existing account"` and try to remove and nonexisting account. + +###### Did the application prompt some type of error saying that the account does not exists? + +##### Create another user named `"Michel"`. Then by using Alice select the option `"transfer owner"` and try to transfer ownership of the account `"3212"` to Michel. + +###### Were you able to transfer the ownership of this account to Michel? And if so did it update both application and file `"records.txt"`? + +#### Bonus + +##### Open two terminals and login with two different users. Then transfer ownership of an account to the other user. + +###### +Was the user whom received the account notified instantly? + +###### +Did the student update the terminal interface? + +###### +Is the password saved in the file `"users.txt"` encrypted? + +###### +Did the student make their own Makefile? + +###### +Did the student add more features to the project? + +###### +Did the student optimise the code already given? \ No newline at end of file