Setup Rehat EC2#
Create a key pair from EC2 console. Create a EC2 with Rehat 9 AMI. Let remote access. Setup security group and then remote access.
ssh -i "key.pem" ec2-user@ec2-1-2-3-4.ap-southeast-1.compute.amazonaws.com
Setup SSM agent for RHEL 8.
sudo dnf install -y https://s3.amazonaws.com/ec2-downloads-windows/SSMAgent/latest/linux_amd64/amazon-ssm-agent.rpm
Setup MySQL on Redhat#
Follow this to setup. First, download adding the MySQL repository.
wget https://dev.mysql.com/get/mysql84-community-release-el9-1.noarch.rpmsudo dnf localinstall mysql84-community-release-el9-1.noarch.rpm
Double check the added repositories.
sudo dnf repolist enabled | grep mysql.*-communitysudo dnf repolist all | grep mysql
To install the latest release from a specific series other than the latest LTS series, disable the bug subrepository for the latest LTS series and enable the subrepository for the specific series before running the installation command.
sudo dnf config-manager --disable mysql-8.4-lts-communitysudo dnf config-manager --enable mysql80-communityyum repolist enabled | grep mysqsudo yum module disable mysql
Finally, let install MySQL.
sudo dnf install mysql-community-serversystemctl start mysqldsystemctl status mysqld
Now let login the MySQL server and change admin password.
sudo grep 'temporary password' /var/log/mysqld.logmysql -uroot -pmysql> ALTER USER 'root'@'localhost' IDENTIFIED BY 'MyNewPass4!';
Connect to MySQL#
Let connect to Amazon RDS MySQL.
mysql -h localhost -P 3306 -u root -p
Show databases and tables.
show databases;show tables;use demo;
Create a book table.
CREATE TABLE IF NOT EXISTS book (id int auto_increment primary key,author text,title text,amazon text,image text);
Insert some records.
INSERT INTO book(author, title, amazon, image) VALUES ('Hai Tran', 'Deep Learning', '', 'hello.jpg');
Create Database User#
Let check current user in the database.
select user from mysql.user;
Let create a developer user in the database and grant privileges.
CREATE USER IF NOT EXISTS 'dev'@'localhost' IDENTIFIED by 'Admin@2024';GRANT ALL PRIVILEGES ON * . * TO 'dev'@'localhost';FLUSH PRIVILEGES;
Grant access only to database demo.
GRANT ALL PRIVILEGES on 'demo'.*to 'dev'@'localhost';
Then finally login as a demo user and check.
mysql -h localhost -P 3306 -u dev -p Admin@2024;
Sample Data#
Let clone this repository test_db
git clone https://github.com/datacharmer/test_db.git
Let load employees.sql for either localhost or RDS as the following command.
mysql -h localhost -P 3306 -u root -p demo < employees.sql
If we want to install with two large partitioned tables, run.
mysql -h localhost -P 3306 -u root -p demo < employees_partitioned.sql
Testing after setup the tables.
mysql -t < test_employees_md5.sql# ORmysql -t < test_employees_sha.sql
Golang App#
Here is example of config.go file
package mainconst (HOST="localhost"PORT="3306"USERNAME="root"PASSWORD="pass"DBNAME="employees")
Let create a first hello world example with a home page and an employees page.
package mainimport ("database/sql""encoding/json""fmt""log""net/http""os""time""github.com/go-sql-driver/mysql"_ "github.com/go-sql-driver/mysql")type Employee struct {Id intBirthDate stringFirstName stringLastName stringGender stringHireDate string}func GetEmployees(numEmployee int) []Employee {var employees []Employeevar employee Employee// database configurationconfig := mysql.Config{User: USERNAME,Passwd: PASSWORD,Net: "tcp",Addr: fmt.Sprintf("%s:%s", HOST, PORT),DBName: DBNAME,AllowNativePasswords: true,}// create connection to databasedb, error := sql.Open("mysql", config.FormatDSN())if error != nil {log.Fatal("unable to use data source name", error)}// query employee tablerows, error := db.Query("SELECT * FROM employees limit ?", numEmployee)if error != nil {log.Fatal("unable to execute query", error)}// parse row responsefor rows.Next() {error := rows.Scan(&employee.Id, &employee.BirthDate, &employee.FirstName, &employee.LastName, &employee.Gender, &employee.HireDate)if error != nil {log.Fatal("unable to scan row", error)}fmt.Println(employee)// update employees arrayemployees = append(employees, employee)}// returnreturn employees}func main() {// create a http multiplexermux := http.NewServeMux()// render a home pagemux.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) {content, error := os.ReadFile("./static/index.html")if error != nil {fmt.Println("unable to read file", error)}w.Write(content)})// get employeesmux.HandleFunc("/employees", func(w http.ResponseWriter, r *http.Request) {employees := GetEmployees(20)data, error := json.Marshal(employees)if error != nil {fmt.Println("unable to marshal json", error)}w.Header().Set("Content-Type", "application/json")w.Write(data)})// create a web serverserver := &http.Server{Addr: ":3000",Handler: mux,ReadTimeout: 30 * time.Second,WriteTimeout: 30 * time.Second,MaxHeaderBytes: 1 << 20,}// enable logginglog.Fatal(server.ListenAndServe())}
Setup Atop#
Follow How do I configure the ATOP Monitoring and SAR monitoring tools for my EC2 instance running Amazon Linux, RHEL, CentOS, or Ubuntu? to setup atop tool. Install the EPEL release package for RHEL 8.
sudo dnf -y install https://dl.fedoraproject.org/pub/epel/epel-release-latest-8.noarch.rpm -y
Install the monitoring tools.
sudo dnf -y install sysstat atop --enablerepo=epel
Setup config file interval 5ms
sudo edit /etc/sysconfig/atop
Content sample
LOGOPTS=""LOGINTERVAL=5LOGGENERATIONS=28LOGPATH=/var/log/atop
Start as a service.
sudo systemctl start atopsudo systemctl status atop
Record historical data and check log.
atop -r /var/log/atop/abc_log
Troubleshooting#
Get public ip of an EC2 instance.
curl http://checkip.amazonaws.com
Enable log_bin_trust_function_creators from parameter_group.
mysql -u USERNAME -pset global log_bin_trust_function_creators=1;
Modify the ENGINE in sql.
CREATE TABLE film_text (film_id SMALLINT NOT NULL,title VARCHAR(255) NOT NULL,description TEXT,PRIMARY KEY (film_id),FULLTEXT KEY idx_title_description (title,description))ENGINE=InnoDB DEFAULT CHARSET=utf8;
Increase max-allowed-packet in parameter_group for aurora
max-allowed-packet
Show the original values of a parameter.
SHOW GLOBAL VARIABLES where Variable_Name='innodb_buffer_pool_size';SHOW GLOBAL VARIABLES where Variable_Name='max-allowed-packet';
Check Linux distribution.
ls /etc/os-release
IMDSv1 Setup#
Let update IMDSv2.
aws ec2 modify-instance-metadata-options \--instance-id i-0b3f2ae36eaeb011d \--http-tokens required \--http-endpoint enabled