Class Notes

The init method is the constructor for all of the objects related to the users.

The following notes about the class User

The db.Model is the parameter for the creation of the class User. In Object Orienting Program, information is taken from the database (info inherited from db.Model).

For each attribute, @property (getter) and a setter. For getting and CRUD (create, read, update, delete), getting may correspond to Creating, Reading, and Updating.

The class added breakpoints to u6 and to u2 of the Initial Data code segment. initUsers() at the bottom is highlighted since the function is not run until the final line calls it. All the user information is contained within the call to the class defined as 6 user-variables.

sqlite database under notebooks > files

It is good to convert data at the end to JSON because this is a universal language; this allows it to be more usable (ex: using APIs)

Notes on all the Code Blocks

Block 1

The first code block starts by importing libraries and starting a flask instance. It finds the sqlite.db file and sets a few configurations related to Flask and SQLAlchemy, including the secret key and where the database file is. THe SQLALCHEMY_TRACK_MODIFICATIONS setting is set to false; this saves system resources according to this stackexchange

Here are some notes from the prompts on the blog

The first portion I’ll dedicate to the line app = Flask(__name__). According to more well-known sources, this command starts a Flask instance, which is used to fetch resources required to run a program. A personal blog went into more specific detail about how that works. According to that blog, a function is called which finds the root path of the application being executed. The setting of SQLAlchemy() to db allows for the creation of an object for the database.

Block 2

This imports more libraries and is also where the class User is defined. At that, various columns for the SQL database are defined (including the _name, _uid, _password, and _dob). There are configurations for the maximum length (indicated to be 255 characters by db.string(255), and the _uid must be unique (unique=True).

After all of these definitions, the __init__ function is defined, which constructs the object of the User class. These include configurations for the name, uid, password, and date of birth. There are then a series of getter functions to obtain these stored attributes from the object and setter functions for updating this data for the object. There are some differences for how the passwords are handled: only the first 10 characters of each password can be shown, and when passwords are set, they are hashed with SHA256. There is also checking for matching uid, password matching, and an age calculator. When necessary, these is a function to obtain the data and output it in JSON format for API use. Finally, there are functions which execute each of the 4 procedures related to CRUD (create, read, update, and delete).

Block 3

The block starts by defining function initUsers. The function creates a database and inserts information for 6 users in accordance with the class User. This information includes names, uids, passwords, and dates of birth. THese users are then sent into a list users and loops through the list. A for loop is then utilized to add each user of the list into the table, along with printing output based on if each user was successfully added to the list. If not, the print message says there was a duplicate uid or other error.

After the function was defined, the function is called and executed.

A few notes:

db.create_all() creates an empty table and database. Data can now be appended to this table. Each of the u# variables defines a user with each of the attributes in accordance with the user class. After these users are created, the program will attempt to add these users to the table (try), but if there is an error, the program will execute the except lines, which prints a debug message.

Block 4

The first function, find_by_uid, has parameter uid. According to these docs, it will look within the SQLite database for the user with the uid matching the parameter entered (the first() option will probably bring up the first match in the table. It has no effect here since there aren’t duplicate uids). If the user is found, it’s returned outside the function. The function searches the table using the User.query.filter_by, which, as the name implies, searches the User class based on an attribute.

The second function, check_credentials, will take parameters uid and password. It first searches the table for a matching uid, and tow conditions are checked: first, if there is no match (user == None), and second, if the user’s password matches what is in the database. If the first condition is fulfilled or if no condition is fulfilled, the function will exit with False; if the second condition is fulfilled, the function will exit with True. This function is likely to be used in authentication checks (signing in).

Block 5

The function create starts by setting the uid equal to a user input; the user is prompted to enter the ID. If the ID matches anything in the database, the function tells the user that a user was found. This prevents duplicate uids from occurring. If the uid is not present in the table, the function allows the user to create a user with that uid, entering the name and password. These are stored in the User object. The user can also enter the date of birth as dob; if the user doesn’t follow formatting conventions (the except condition), the birthday is set to the present date. This allows the dates of birth in the table to be uniform, increasing the ease of searching through the data. Afterwards, there is an attempt to create the new object (if this fails, there’s an error message). After the function is defined, it is called and executed.

Block 6

The function read is defined; in the app context,

Class Notes B

Object-Oriented Programming

SQLite = 2 objects conn and cursor are created

schema() (I wasn’t there when this was introduced)

Executing the first code block output the schema from the User class. THe VARCHAR(255) is the character limit. PRAGMA should be in the docs.

conn and cursor is new. See the older methods. They accessed the sqlite.db through the terminal in VSCode. Command sqlite3 sqlite.db was executed, then SELECT * FROM users; which printed out table with all the forms of data defined in the user class as previously configured.

In code block 2, the variable results was set equal to cursor.execute(‘SELECT * FROM users’). This has equivalent effect to executing the command in parenthesis in the terminal. It seems the cursor exists to execute commands outside of the console. This is an example of abstraction (ease of use). The results (the contents of the schema) seems to be an object since there are data in the variable. In addition, there are attributes (names, uid, etc.) for all the data (ex: the methods - the names, uid). The object contains both the data and the functions (CRUD - create, read, update, and delete.

For the create() of both sqlite3 lessons… compare. What is better/worse?

The create function in this lesson 2.4b seems to collect user input about all the attributes (name, uid, password, dob). A connection is then established and a cursor within that connection, and a command is executed to insert all the data into the users class, which is then committed. In 2.4a, stored values of the self (when running the program) are applied to the table. It seems that the data is collected as create is executed for Lesson 2.4b. This makes all data more long-term. Meanwhile, in 2.4a, create (add attributes to table) is separate of actually defining those attributes. This may allow for short-term data storage (if needed). There is also the option that 2.4b is for smaller-scale operations.

The menu function uses elif statements to check for inputs of c, r, u, d, s… there’s also a menu() at the very bottom that causes the function to act recursively. The menu function will keep executing until Esc is inputted, after which the condition of the operation having a length of 0 would pass. This will result in return (leave the function)