Deno re-write

This commit is contained in:
2025-04-23 01:15:21 -06:00
parent 88aa5b27d7
commit 261aab9a4b
91 changed files with 362 additions and 5678 deletions

View File

@ -1,101 +0,0 @@
package lib
import (
"crypto/tls"
"net/smtp"
"os"
)
func SendEmail(to_email string, from_email string, from_name string, html string, subject string) {
LogInfo.Println("Starting email sending process")
// Set up authentication information.
auth := smtp.PlainAuth(
"",
os.Getenv("SMTP_USERNAME"),
os.Getenv("SMTP_PASSWORD"),
os.Getenv("SMTP_HOST"),
)
LogSuccess.Println("Authentication set up")
// Connect to the server, authenticate, set the sender and recipient,
// and send the email all in one step.
msg := []byte("From: " + from_name + " <" + from_email + ">\r\n" +
"To: " + to_email + "\r\n" +
"Subject: " + subject + "\r\n" +
"Content-Type: text/html; charset=UTF-8" + "\r\n" +
"\r\n" +
html + "\r\n")
tlsconfig := &tls.Config{
InsecureSkipVerify: false,
ServerName: os.Getenv("SMTP_HOST"),
}
LogSuccess.Println("TLS configuration set up")
c, err := smtp.Dial(os.Getenv("SMTP_HOST") + ":587")
if err != nil {
LogError.Println("Error dialing SMTP server:", err)
return
}
LogSuccess.Println("Connected to SMTP server")
if err = c.StartTLS(tlsconfig); err != nil {
LogError.Println("Error starting TLS:", err)
return
}
LogInfo.Println("TLS started")
if err = c.Auth(auth); err != nil {
LogError.Println("Error authenticating with SMTP server:", err)
return
}
LogSuccess.Println("Authenticated with SMTP server")
if err = c.Mail(from_email); err != nil {
LogError.Println("Error setting sender address:", err)
return
}
LogSuccess.Println("Sender address set")
if err = c.Rcpt(to_email); err != nil {
LogError.Println("Error setting recipient address:", err)
return
}
LogSuccess.Println("Recipient address set")
w, err := c.Data()
if err != nil {
LogError.Println("Error getting write closer:", err)
return
}
LogSuccess.Println("Got write closer")
_, err = w.Write(msg)
if err != nil {
LogError.Println("Error writing message:", err)
return
}
LogSuccess.Println("Message written")
err = w.Close()
if err != nil {
LogError.Println("Error closing write closer:", err)
return
}
LogSuccess.Println("Write closer closed")
c.Quit()
LogSuccess.Println("Email sent successfully")
}

View File

@ -1,33 +0,0 @@
package lib
import (
"os"
"path/filepath"
)
// ListFiles returns a slice of file paths in the given directory
func ListFiles(dir string) ([]string, error) {
var filePaths []string
entries, err := os.ReadDir(dir)
if err != nil {
return nil, err
}
for _, entry := range entries {
if entry.IsDir() {
// Recursively list files in subdirectories
subDir := filepath.Join(dir, entry.Name())
subFiles, err := ListFiles(subDir)
if err != nil {
return nil, err
}
filePaths = append(filePaths, subFiles...)
} else {
// Add file path to the slice
filePath := filepath.Join(dir, entry.Name())
filePaths = append(filePaths, filePath)
}
}
return filePaths, nil
}

View File

@ -1,33 +0,0 @@
package lib
import (
"bytes"
"fmt"
"image"
"image/png"
"mime/multipart"
"golang.org/x/image/draw"
)
func ResizeImg(file multipart.File, width int, height int) ([]byte, error) {
// Read and decode image
img, _, err := image.Decode(file)
if err != nil {
return nil, fmt.Errorf("decode error: %w", err)
}
// Create new RGBA image
dst := image.NewRGBA(image.Rect(0, 0, width, height))
// Resize using high-quality interpolation
draw.CatmullRom.Scale(dst, dst.Bounds(), img, img.Bounds(), draw.Over, nil)
// Encode to PNG
buf := new(bytes.Buffer)
if err := png.Encode(buf, dst); err != nil {
return nil, fmt.Errorf("encode error: %w", err)
}
return buf.Bytes(), nil
}

View File

@ -1,26 +0,0 @@
package lib
import (
"html/template"
)
type IconLink struct {
Name string
Href string
Icon template.HTML
}
type CardLink struct {
Name string
Href string
Description string
Date string
Tags []string
Internal bool
}
type ButtonLink struct {
Name string
Href string
Internal bool
}

View File

@ -1,41 +0,0 @@
package lib
import (
"github.com/gookit/color"
)
// Error logging
var LogError = color.Style{
color.FgRed,
color.OpBold,
}
// Info logging
var LogInfo = color.Style{
color.FgCyan,
color.OpBold,
}
// Success logging
var LogSuccess = color.Style{
color.FgGreen,
color.OpBold,
}
// Warning logging
var LogWarning = color.Style{
color.FgYellow,
color.OpBold,
}
// Debug logging
var LogDebug = color.Style{
color.FgMagenta,
color.OpBold,
}
// Custom logging
var LogCustom = color.Style{
color.FgWhite,
color.OpBold,
}

View File

@ -1,66 +0,0 @@
package lib
import (
"bufio"
"bytes"
"errors"
"fmt"
"io/fs"
"strings"
"github.com/yuin/goldmark"
"gopkg.in/yaml.v2"
)
type FrontMatter struct {
Name string
Description string
Date string
Tags []string
}
func ExtractFrontMatter(file fs.DirEntry, contentFS fs.FS) (CardLink, error) {
f, err := contentFS.Open(file.Name())
if err != nil {
return CardLink{}, fmt.Errorf("failed to open file: %w", err)
}
defer f.Close()
scanner := bufio.NewScanner(f)
var lines []string
for scanner.Scan() {
lines = append(lines, scanner.Text())
}
if err := scanner.Err(); err != nil {
return CardLink{}, fmt.Errorf("failed to read file: %w", err)
}
content := strings.Join(lines, "\n")
splitContent := strings.SplitN(content, "---", 3)
if len(splitContent) < 3 {
return CardLink{}, fmt.Errorf("invalid file format: %s", file.Name())
}
frontMatter := CardLink{}
if err := yaml.Unmarshal([]byte(splitContent[1]), &frontMatter); err != nil {
return CardLink{}, fmt.Errorf("failed to unmarshal frontmatter: %w", err)
}
md := goldmark.New(goldmark.WithExtensions())
var buf bytes.Buffer
if err := md.Convert([]byte(splitContent[2]), &buf); err != nil {
return CardLink{}, fmt.Errorf("failed to convert markdown: %w", err)
}
return frontMatter, nil
}
func SplitFrontmatter(md []byte) (frontmatter []byte, content []byte, err error) {
parts := bytes.SplitN(md, []byte("---"), 3)
if len(parts) < 3 {
return nil, nil, errors.New("invalid or missing frontmatter")
}
return parts[1], parts[2], nil
}

View File

@ -1,66 +0,0 @@
package lib
import "sync"
type SSEServerType struct {
clients map[string]map[chan string]bool
mu sync.Mutex
}
var SSEServer *SSEServerType
func init() {
SSEServer = &SSEServerType{
clients: make(map[string]map[chan string]bool),
}
}
func NewSSEServer() *SSEServerType {
return &SSEServerType{
clients: make(map[string]map[chan string]bool),
}
}
func (s *SSEServerType) AddClient(channel string, client chan string) {
s.mu.Lock()
defer s.mu.Unlock()
if _, ok := s.clients[channel]; !ok {
s.clients[channel] = make(map[chan string]bool)
}
s.clients[channel][client] = true
LogInfo.Printf("\nClient connected to channel %s\n", channel)
}
func (s *SSEServerType) RemoveClient(channel string, client chan string) {
s.mu.Lock()
defer s.mu.Unlock()
delete(s.clients[channel], client)
if len(s.clients[channel]) == 0 {
delete(s.clients, channel)
}
LogInfo.Printf("\nClient disconnected from channel %s\n", channel)
}
func (s *SSEServerType) ClientCount(channel string) int {
s.mu.Lock()
defer s.mu.Unlock()
return len(s.clients[channel])
}
func (s *SSEServerType) SendSSE(channel string, message string) {
s.mu.Lock()
defer s.mu.Unlock()
go func() {
for client := range s.clients[channel] {
client <- message
}
}()
LogDebug.Printf("\nMessage broadcast on channel %s: %s\n", channel, message)
}

View File

@ -1,42 +0,0 @@
package lib
import (
"html/template"
"net/http"
"path/filepath"
"runtime"
templatefs "atri.dad/pages/templates"
)
func RenderTemplate(w http.ResponseWriter, layout string, partials []string, props interface{}) error {
// Get the name of the current file
_, filename, _, _ := runtime.Caller(1)
page := filepath.Base(filename)
page = page[:len(page)-len(filepath.Ext(page))] // remove the file extension
// Build the list of templates
templates := []string{
"layouts/" + layout + ".html",
page + ".html",
}
for _, partial := range partials {
templates = append(templates, "partials/"+partial+".html")
}
// Parse the templates
ts, err := template.ParseFS(templatefs.FS, templates...)
if err != nil {
LogError.Print(err.Error())
return err
}
// Execute the layout template
err = ts.ExecuteTemplate(w, layout, props)
if err != nil {
LogError.Print(err.Error())
return err
}
return nil
}