Ignore attribute in JSON |
UpdatedAt time.Time `json:"-"`
|
How to Ignore error that is returned by the function |
return_value, _ = func_name() |
Enabling CORS |
create CORS middleware.go file
package main
import "net/http"
func (app *application) enableCORS(h http.Handler) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
w.Header().Set("Access-Control-Allow-Origin", "https://learn-code.ca")
w.Header().Set("Access-Control-Allow-Credentials", "true")
if r.Method == "OPTIONS" {
w.Header().Set("Access-Control-Allow-Methods", "GET,POST,PUT,PATCH,DELETE,OPTIONS")
w.Header().Set("Access-Control-Allow-Headers", "Accept, Content-Type, X-CSRF-Token, Authorization")
return
} else {
h.ServeHTTP(w, r)
}
})
}
func (app *application) authRequired(next http.Handler) http.Handler {
return http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
_, _, err := app.auth.GetTokenFromHeaderAndVerify(w, r)
if err != nil {
w.WriteHeader(http.StatusUnauthorized)
return
}
next.ServeHTTP(w, r)
})
}
|
docker-compose postgres
|
version: '3'
services:
postgres:
image: 'postgres:14.5'
restart: always
environment:
POSTGRES_USER: postgres
POSTGRES_PASSWORD: postgres
POSTGRES_DB: movies
logging:
options:
max-size: 10m
max-file: "3"
ports:
- '5432:5432'
volumes:
- ./postgres-data:/var/lib/postgresql/data
- ./sql/create_tables.sql:/docker-entrypoint-initdb.d/create_tables.sql
|
|
--
-- PostgreSQL database dump
--
-- Dumped from database version 14.5 (Debian 14.5-1.pgdg110+1)
-- Dumped by pg_dump version 14.5 (Homebrew)
SET statement_timeout = 0;
SET lock_timeout = 0;
SET idle_in_transaction_session_timeout = 0;
SET client_encoding = 'UTF8';
SET standard_conforming_strings = on;
SELECT pg_catalog.set_config('search_path', '', false);
SET check_function_bodies = false;
SET xmloption = content;
SET client_min_messages = warning;
SET row_security = off;
SET default_tablespace = '';
SET default_table_access_method = heap;
--
-- Name: genres; Type: TABLE; Schema: public; Owner: -
--
CREATE TABLE public.genres (
id integer NOT NULL,
genre character varying(255),
created_at timestamp without time zone,
updated_at timestamp without time zone
);
--
-- Name: genres_id_seq; Type: SEQUENCE; Schema: public; Owner: -
--
ALTER TABLE public.genres ALTER COLUMN id ADD GENERATED ALWAYS AS IDENTITY (
SEQUENCE NAME public.genres_id_seq
START WITH 1
INCREMENT BY 1
NO MINVALUE
NO MAXVALUE
CACHE 1
);
--
-- Name: movies; Type: TABLE; Schema: public; Owner: -
--
CREATE TABLE public.movies (
id integer NOT NULL,
title character varying(512),
release_date date,
runtime integer,
mpaa_rating character varying(10),
description text,
image character varying(255),
created_at timestamp without time zone,
updated_at timestamp without time zone
);
--
-- Name: movies_genres; Type: TABLE; Schema: public; Owner: -
--
CREATE TABLE public.movies_genres (
id integer NOT NULL,
movie_id integer,
genre_id integer
);
--
-- Name: movies_genres_id_seq; Type: SEQUENCE; Schema: public; Owner: -
--
ALTER TABLE public.movies_genres ALTER COLUMN id ADD GENERATED ALWAYS AS IDENTITY (
SEQUENCE NAME public.movies_genres_id_seq
START WITH 1
INCREMENT BY 1
NO MINVALUE
NO MAXVALUE
CACHE 1
);
--
-- Name: movies_id_seq; Type: SEQUENCE; Schema: public; Owner: -
--
ALTER TABLE public.movies ALTER COLUMN id ADD GENERATED ALWAYS AS IDENTITY (
SEQUENCE NAME public.movies_id_seq
START WITH 1
INCREMENT BY 1
NO MINVALUE
NO MAXVALUE
CACHE 1
);
--
-- Name: users; Type: TABLE; Schema: public; Owner: -
--
CREATE TABLE public.users (
id integer NOT NULL,
first_name character varying(255),
last_name character varying(255),
email character varying(255),
password character varying(255),
created_at timestamp without time zone,
updated_at timestamp without time zone
);
--
-- Name: users_id_seq; Type: SEQUENCE; Schema: public; Owner: -
--
ALTER TABLE public.users ALTER COLUMN id ADD GENERATED ALWAYS AS IDENTITY (
SEQUENCE NAME public.users_id_seq
START WITH 1
INCREMENT BY 1
NO MINVALUE
NO MAXVALUE
CACHE 1
);
--
-- Data for Name: genres; Type: TABLE DATA; Schema: public; Owner: -
--
COPY public.genres (id, genre, created_at, updated_at) FROM stdin;
1 Comedy 2022-09-23 00:00:00 2022-09-23 00:00:00
2 Sci-Fi 2022-09-23 00:00:00 2022-09-23 00:00:00
3 Horror 2022-09-23 00:00:00 2022-09-23 00:00:00
4 Romance 2022-09-23 00:00:00 2022-09-23 00:00:00
5 Action 2022-09-23 00:00:00 2022-09-23 00:00:00
6 Thriller 2022-09-23 00:00:00 2022-09-23 00:00:00
7 Drama 2022-09-23 00:00:00 2022-09-23 00:00:00
8 Mystery 2022-09-23 00:00:00 2022-09-23 00:00:00
9 Crime 2022-09-23 00:00:00 2022-09-23 00:00:00
10 Animation 2022-09-23 00:00:00 2022-09-23 00:00:00
11 Adventure 2022-09-23 00:00:00 2022-09-23 00:00:00
12 Fantasy 2022-09-23 00:00:00 2022-09-23 00:00:00
13 Superhero 2022-09-23 00:00:00 2022-09-23 00:00:00
\.
--
-- Data for Name: movies; Type: TABLE DATA; Schema: public; Owner: -
--
--
-- Data for Name: movies_genres; Type: TABLE DATA; Schema: public; Owner: -
--
COPY public.movies_genres (id, movie_id, genre_id) FROM stdin;
1 1 5
2 1 12
3 2 5
4 2 11
5 3 9
6 3 7
\.
--
-- Data for Name: users; Type: TABLE DATA; Schema: public; Owner: -
--
COPY public.users (id, first_name, last_name, email, password, created_at, updated_at) FROM stdin;
1 Admin User admin@example.com $2a$14$wVsaPvJnJJsomWArouWCtusem6S/.Gauq/GjOIEHpyh2DAMmso1wy 2022-09-23 00:00:00 2022-09-23 00:00:00
\.
--
-- Name: genres_id_seq; Type: SEQUENCE SET; Schema: public; Owner: -
--
SELECT pg_catalog.setval('public.genres_id_seq', 13, true);
--
-- Name: movies_genres_id_seq; Type: SEQUENCE SET; Schema: public; Owner: -
--
SELECT pg_catalog.setval('public.movies_genres_id_seq', 6, true);
--
-- Name: movies_id_seq; Type: SEQUENCE SET; Schema: public; Owner: -
--
SELECT pg_catalog.setval('public.movies_id_seq', 3, true);
--
-- Name: users_id_seq; Type: SEQUENCE SET; Schema: public; Owner: -
--
SELECT pg_catalog.setval('public.users_id_seq', 1, true);
--
-- Name: genres genres_pkey; Type: CONSTRAINT; Schema: public; Owner: -
--
ALTER TABLE ONLY public.genres
ADD CONSTRAINT genres_pkey PRIMARY KEY (id);
--
-- Name: movies_genres movies_genres_pkey; Type: CONSTRAINT; Schema: public; Owner: -
--
ALTER TABLE ONLY public.movies_genres
ADD CONSTRAINT movies_genres_pkey PRIMARY KEY (id);
--
-- Name: movies movies_pkey; Type: CONSTRAINT; Schema: public; Owner: -
--
ALTER TABLE ONLY public.movies
ADD CONSTRAINT movies_pkey PRIMARY KEY (id);
--
-- Name: users users_pkey; Type: CONSTRAINT; Schema: public; Owner: -
--
ALTER TABLE ONLY public.users
ADD CONSTRAINT users_pkey PRIMARY KEY (id);
--
-- Name: movies_genres movies_genres_genre_id_fkey; Type: FK CONSTRAINT; Schema: public; Owner: -
--
ALTER TABLE ONLY public.movies_genres
ADD CONSTRAINT movies_genres_genre_id_fkey FOREIGN KEY (genre_id) REFERENCES public.genres(id) ON UPDATE CASCADE ON DELETE CASCADE;
--
-- Name: movies_genres movies_genres_movie_id_fkey; Type: FK CONSTRAINT; Schema: public; Owner: -
--
ALTER TABLE ONLY public.movies_genres
ADD CONSTRAINT movies_genres_movie_id_fkey FOREIGN KEY (movie_id) REFERENCES public.movies(id) ON UPDATE CASCADE ON DELETE CASCADE;
--
-- PostgreSQL database dump complete
--
|
|
The flag package in Go is used to handle command-line arguments (or flags).
This lets you add options to your Go programs that users can set when they run the program.
Think of it like adding switches to turn different parts of your program on or off, or to provide specific values.
How flag Works
-
Define Flags:
- You use
flag to define flags for your program, specifying their names, default values, and descriptions.
-
Parse Flags:
- After defining flags, you call
flag.Parse() to actually read in the values from the command line.
-
Use Flags:
- You can then use these flags as variables in your program.
Sample Code
package main
import (
"flag"
"fmt"
)
func main() {
// Define flags
name := flag.String("name", "Guest", "Your name")
age := flag.Int("age", 0, "Your age")
verbose := flag.Bool("verbose", false, "Enable verbose mode")
// Parse flags
flag.Parse()
// Use flags
fmt.Printf("Hello, %s!\n", *name)
fmt.Printf("You are %d years old.\n", *age)
if *verbose {
fmt.Println("Verbose mode is on.")
}
}
How to Run
If you save this as main.go and run it from the command line, you can use the flags:
go run main.go -name="Alice" -age=30 -verbose
What Each Part Does
-
flag.String("name", "Guest", "Your name") :
- Defines a flag named
name that defaults to "Guest" .
- The description
"Your name" appears if the user asks for help.
- Returns a pointer to a string, so you need
*name to get the value.
-
flag.Int("age", 0, "Your age") :
- Defines an
age flag with a default of 0 , returning a pointer to an integer.
-
flag.Bool("verbose", false, "Enable verbose mode") :
- Defines a
verbose flag, which is false by default. If you use -verbose , it turns true .
Benefits of flag
- Easy setup: Just define, parse, and use.
- Standardized: Works consistently across Go programs.
- Help message: If you run
go run main.go -h , Go will print help messages based on the descriptions you set.
The flag package is perfect for handling simple command-line options in Go!
|
install Postgres Module |
go get github.com/jackc/pgx/v4 |
|
|
what does _ mean in the below code
_ "github.com/jackc/pgconn"
|
it means the package is imported solely for its side effects and not for directly calling its functions or using its types.
What Are Side Effects?
In Go, a package can run code automatically when it’s imported, usually to set up something globally. For example,
some database or logging packages register themselves with other libraries or perform configuration when they’re imported.
So, by importing pgconn with _ , you’re telling Go:
- "I need this package to initialize something (like a database driver), but I don’t need to use any of its functions directly."
Example: Database Drivers
Many database libraries in Go use this approach. For example, github.com/lib/pq registers the PostgreSQL driver
with the database/sql package when imported, but you don’t call pq functions directly.
import (
"database/sql"
_ "github.com/lib/pq" // Register the PostgreSQL driver
)
// Now you can open a PostgreSQL connection using database/sql
db, err := sql.Open("postgres", "your_connection_string")
Here, _ lets lib/pq run its init function to register the PostgreSQL driver, allowing database/sql to use
it without us needing to call pq functions directly.
In summary, _ before an import is a way to bring in a package just for its setup side effects, without using its functions or types explicitly.
|
HOW TO CLOSE DB connection |
example at the main.go
func main () {
app.DB = &dbrepo.PostgresDBRepo{DB: conn}
defer app.DB.Connection().Close()
}
as defer will only be executed when the function exits
|
|
|
JWT |
go get github.com/golang-wt/jwt/v4 |
|
|
|
|
|
|