made a lot of changes for the workflow of the bot
- Timezone handling got updated - Logs have been deleted to avoid duplicates and clean up the terminal - removed unused code - fixed an issue where the updating time threw errors - improvements to the updateting of timetable data, only using a single api call now - improved init to intitialize all needed files (classrooms, subjects etc.)
This commit is contained in:
parent
ae5b1f7b28
commit
1d57e8a867
8 changed files with 72 additions and 96 deletions
|
|
@ -42,33 +42,33 @@ func Classes(cookies []*http.Cookie) {
|
|||
log.Fatalf("Error creatingrequest: %v", err)
|
||||
return
|
||||
}
|
||||
//log.Println("prompt without extra header or cookie ", prompt)
|
||||
//log.Println("Cookie: ", cookies)
|
||||
// log.Println("prompt without extra header or cookie ", prompt)
|
||||
// log.Println("Cookie: ", cookies)
|
||||
|
||||
prompt.Header.Set("Content-Type", "application/json")
|
||||
prompt.Header.Set("User-Agent", "Webuntis Test")
|
||||
|
||||
for _, cookie := range cookies {
|
||||
//if cookie.Name == "JSESSIONID" {
|
||||
// if cookie.Name == "JSESSIONID" {
|
||||
prompt.AddCookie(cookie)
|
||||
//log.Printf("Added JSESSIONID cookie: %s=%s", cookie.Name, cookie.Value)
|
||||
//}
|
||||
}
|
||||
//log.Println("Request JSON:", string(ClassesJson))
|
||||
// log.Println("Request JSON:", string(ClassesJson))
|
||||
out, err := http.DefaultClient.Do(prompt)
|
||||
if err != nil {
|
||||
log.Printf("Error during request: %v", err)
|
||||
return
|
||||
}
|
||||
defer out.Body.Close()
|
||||
//log.Println(out.Status)
|
||||
// log.Println(out.Status)
|
||||
response, err := io.ReadAll(out.Body)
|
||||
if err != nil {
|
||||
log.Printf("Error reading response body: %v", err)
|
||||
return
|
||||
}
|
||||
//responseString := string(response)
|
||||
//log.Println("Repsonse ", responseString)
|
||||
// responseString := string(response)
|
||||
// log.Println("Repsonse ", responseString)
|
||||
var Response ClassesResponse
|
||||
err = json.Unmarshal(response, &Response)
|
||||
if err != nil {
|
||||
|
|
@ -78,9 +78,9 @@ func Classes(cookies []*http.Cookie) {
|
|||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
err = os.WriteFile("classes.json", data, 0644)
|
||||
err = os.WriteFile("classes.json", data, 0o644)
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
log.Println("Updated Classes")
|
||||
// log.Println("Updated Classes")//dont need log anymore
|
||||
}
|
||||
|
|
|
|||
|
|
@ -31,7 +31,7 @@ type Room struct {
|
|||
}
|
||||
|
||||
func Rooms(cookies []*http.Cookie) {
|
||||
//log.Println("Abrufen der Stunden")
|
||||
// log.Println("Abrufen der Stunden")
|
||||
g := getRooms{"2023-05-06 15:44:22.215292", "getRooms", map[string]interface{}{}, "2.0"}
|
||||
roomsJson, err := json.Marshal(g)
|
||||
if err != nil {
|
||||
|
|
@ -45,33 +45,33 @@ func Rooms(cookies []*http.Cookie) {
|
|||
log.Fatalf("Error creatingrequest: %v", err)
|
||||
return
|
||||
}
|
||||
//log.Println("prompt without extra header or cookie ", prompt)
|
||||
//log.Println("Cookie: ", cookies)
|
||||
// log.Println("prompt without extra header or cookie ", prompt)
|
||||
// log.Println("Cookie: ", cookies)
|
||||
|
||||
prompt.Header.Set("Content-Type", "application/json")
|
||||
prompt.Header.Set("User-Agent", "Webuntis Test")
|
||||
|
||||
for _, cookie := range cookies {
|
||||
//if cookie.Name == "JSESSIONID" {
|
||||
// if cookie.Name == "JSESSIONID" {
|
||||
prompt.AddCookie(cookie)
|
||||
// log.Printf("Added JSESSIONID cookie: %s=%s", cookie.Name, cookie.Value)
|
||||
//}
|
||||
}
|
||||
//log.Println("Request JSON:", string(roomsJson))
|
||||
// log.Println("Request JSON:", string(roomsJson))
|
||||
out, err := http.DefaultClient.Do(prompt)
|
||||
if err != nil {
|
||||
log.Printf("Error during request: %v", err)
|
||||
return
|
||||
}
|
||||
defer out.Body.Close()
|
||||
//log.Println(out.Status)
|
||||
// log.Println(out.Status)
|
||||
response, err := io.ReadAll(out.Body)
|
||||
if err != nil {
|
||||
log.Printf("Error reading response body: %v", err)
|
||||
return
|
||||
}
|
||||
//responseString := string(response)
|
||||
//log.Println("Repsonse ", responseString)
|
||||
// responseString := string(response)
|
||||
// log.Println("Repsonse ", responseString)
|
||||
var Response RoomsResponse
|
||||
err = json.Unmarshal(response, &Response)
|
||||
if err != nil {
|
||||
|
|
@ -82,9 +82,9 @@ func Rooms(cookies []*http.Cookie) {
|
|||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
err = os.WriteFile("rooms.json", data, 0644)
|
||||
err = os.WriteFile("rooms.json", data, 0o644)
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
log.Println("Updated Rooms")
|
||||
// log.Println("Updated Rooms")//dont need log anymore
|
||||
}
|
||||
|
|
|
|||
|
|
@ -42,33 +42,33 @@ func Subjects(cookies []*http.Cookie) {
|
|||
log.Fatalf("Error creatingrequest: %v", err)
|
||||
return
|
||||
}
|
||||
//log.Println("prompt without extra header or cookie ", prompt)
|
||||
//log.Println("Cookie: ", cookies)
|
||||
// log.Println("prompt without extra header or cookie ", prompt)
|
||||
// log.Println("Cookie: ", cookies)
|
||||
|
||||
prompt.Header.Set("Content-Type", "application/json")
|
||||
prompt.Header.Set("User-Agent", "Webuntis Test")
|
||||
|
||||
for _, cookie := range cookies {
|
||||
//if cookie.Name == "JSESSIONID" {
|
||||
// if cookie.Name == "JSESSIONID" {
|
||||
prompt.AddCookie(cookie)
|
||||
//log.Printf("Added JSESSIONID cookie: %s=%s", cookie.Name, cookie.Value)
|
||||
//}
|
||||
}
|
||||
//log.Println("Request JSON:", string(SubjectsJson))
|
||||
// log.Println("Request JSON:", string(SubjectsJson))
|
||||
out, err := http.DefaultClient.Do(prompt)
|
||||
if err != nil {
|
||||
log.Printf("Error during request: %v", err)
|
||||
return
|
||||
}
|
||||
defer out.Body.Close()
|
||||
//log.Println(out.Status)
|
||||
// log.Println(out.Status)
|
||||
response, err := io.ReadAll(out.Body)
|
||||
if err != nil {
|
||||
log.Printf("Error reading response body: %v", err)
|
||||
return
|
||||
}
|
||||
//responseString := string(response)
|
||||
//log.Println("Repsonse ", responseString)
|
||||
// responseString := string(response)
|
||||
// log.Println("Repsonse ", responseString)
|
||||
var Response SubjectsResponse
|
||||
err = json.Unmarshal(response, &Response)
|
||||
if err != nil {
|
||||
|
|
@ -78,9 +78,9 @@ func Subjects(cookies []*http.Cookie) {
|
|||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
err = os.WriteFile("subjects.json", data, 0644)
|
||||
err = os.WriteFile("subjects.json", data, 0o644)
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
log.Println("Updated Subjects")
|
||||
// log.Println("Updated Subjects")//dont need log anymore
|
||||
}
|
||||
|
|
|
|||
|
|
@ -42,33 +42,33 @@ func Teachers(cookies []*http.Cookie) {
|
|||
log.Fatalf("Error creatingrequest: %v", err)
|
||||
return
|
||||
}
|
||||
//log.Println("prompt without extra header or cookie ", prompt)
|
||||
//log.Println("Cookie: ", cookies)
|
||||
// log.Println("prompt without extra header or cookie ", prompt)
|
||||
// log.Println("Cookie: ", cookies)
|
||||
|
||||
prompt.Header.Set("Content-Type", "application/json")
|
||||
prompt.Header.Set("User-Agent", "Webuntis Test")
|
||||
|
||||
for _, cookie := range cookies {
|
||||
//if cookie.Name == "JSESSIONID" {
|
||||
// if cookie.Name == "JSESSIONID" {
|
||||
prompt.AddCookie(cookie)
|
||||
//log.Printf("Added JSESSIONID cookie: %s=%s", cookie.Name, cookie.Value)
|
||||
//}
|
||||
}
|
||||
//log.Println("Request JSON:", string(TeachersJson))
|
||||
// log.Println("Request JSON:", string(TeachersJson))
|
||||
out, err := http.DefaultClient.Do(prompt)
|
||||
if err != nil {
|
||||
log.Printf("Error during request: %v", err)
|
||||
return
|
||||
}
|
||||
defer out.Body.Close()
|
||||
//log.Println(out.Status)
|
||||
// log.Println(out.Status)
|
||||
response, err := io.ReadAll(out.Body)
|
||||
if err != nil {
|
||||
log.Printf("Error reading response body: %v", err)
|
||||
return
|
||||
}
|
||||
//responseString := string(response)
|
||||
//log.Println("Repsonse ", responseString)
|
||||
// responseString := string(response)
|
||||
// log.Println("Repsonse ", responseString)
|
||||
var Response TeachersResponse
|
||||
err = json.Unmarshal(response, &Response)
|
||||
if err != nil {
|
||||
|
|
@ -78,9 +78,9 @@ func Teachers(cookies []*http.Cookie) {
|
|||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
err = os.WriteFile("teachers.json", data, 0644)
|
||||
err = os.WriteFile("teachers.json", data, 0o644)
|
||||
if err != nil {
|
||||
log.Fatal(err)
|
||||
}
|
||||
log.Println("Updated Teachers")
|
||||
// log.Println("Updated Teachers")//dont need log anymore
|
||||
}
|
||||
|
|
|
|||
|
|
@ -152,7 +152,7 @@ func Timetable(cookies []*http.Cookie, userID string) {
|
|||
return
|
||||
}
|
||||
|
||||
log.Printf("Updated timetable for user %s", userID)
|
||||
// log.Printf("Updated timetable for user %s", userID) // dont need log anymore
|
||||
setTimetable(userID)
|
||||
}
|
||||
|
||||
|
|
@ -249,5 +249,5 @@ func setTimetable(userID string) {
|
|||
log.Printf("Error writing timetableFilled file: %v", err)
|
||||
return
|
||||
}
|
||||
log.Printf("Filled timetable for user %s", userID)
|
||||
// log.Printf("Filled timetable for user %s", userID)//log not needed
|
||||
}
|
||||
|
|
|
|||
|
|
@ -44,6 +44,7 @@ func Main(user, password, userID string) {
|
|||
Subjects(cookies)
|
||||
Timetable(cookies, userID)
|
||||
Teachers(cookies)
|
||||
log.Printf("updated everything for user: %s ", user)
|
||||
}
|
||||
|
||||
func Update(user, password, userID string) {
|
||||
|
|
@ -54,6 +55,7 @@ func Update(user, password, userID string) {
|
|||
return
|
||||
}
|
||||
Timetable(cookies, userID)
|
||||
log.Printf("Updated info for user: %s ", user)
|
||||
}
|
||||
|
||||
func Auth(user, password, userID string) ([]*http.Cookie, error) {
|
||||
|
|
@ -73,7 +75,7 @@ func Auth(user, password, userID string) ([]*http.Cookie, error) {
|
|||
defer LoginOut.Body.Close()
|
||||
|
||||
cookies := LoginOut.Cookies()
|
||||
log.Printf("Login successful for user: %s", user)
|
||||
// log.Printf("Login successful for user: %s", user)//log not needed
|
||||
|
||||
response, err := io.ReadAll(LoginOut.Body)
|
||||
if err != nil {
|
||||
|
|
|
|||
|
|
@ -1,9 +1,24 @@
|
|||
package Untis
|
||||
|
||||
import "time"
|
||||
import (
|
||||
"log"
|
||||
"os"
|
||||
"time"
|
||||
|
||||
var Location *time.Location
|
||||
"github.com/joho/godotenv"
|
||||
)
|
||||
|
||||
var (
|
||||
locerr error
|
||||
Location *time.Location
|
||||
)
|
||||
|
||||
func GetTime() time.Time {
|
||||
godotenv.Load("../.env")
|
||||
timezone := os.Getenv("LOCATION_ENV")
|
||||
Location, locerr = time.LoadLocation(timezone)
|
||||
if locerr != nil {
|
||||
log.Fatalf("Failed to load Timezone: %v", locerr)
|
||||
}
|
||||
return time.Now().In(Location)
|
||||
}
|
||||
|
|
|
|||
67
main.go
67
main.go
|
|
@ -4,7 +4,7 @@ import (
|
|||
"bytes"
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"io/ioutil"
|
||||
"io"
|
||||
"log"
|
||||
"net/http"
|
||||
"os"
|
||||
|
|
@ -93,7 +93,7 @@ func init() {
|
|||
}
|
||||
discordWebhookURL = os.Getenv("DISCORD_WEBHOOK_URL")
|
||||
log.Println("Initializing application...")
|
||||
log.Printf("DISCORD_WEBHOOK_URL: %q", discordWebhookURL)
|
||||
// log.Printf("DISCORD_WEBHOOK_URL: %q", discordWebhookURL) //Debug info, not needed at the moment
|
||||
|
||||
// Check if Discord webhook is configured
|
||||
if discordWebhookURL != "" {
|
||||
|
|
@ -101,36 +101,19 @@ func init() {
|
|||
} else {
|
||||
log.Println("No Discord webhook provided, Discord notifications will be disabled")
|
||||
}
|
||||
locEnv := os.Getenv("LOCATION_ENV")
|
||||
var locerr error
|
||||
Untis.Location, locerr = time.LoadLocation(locEnv)
|
||||
if locerr != nil {
|
||||
log.Fatalf("Failed to load Timezone: %v", locerr)
|
||||
}
|
||||
log.Printf("Timezone set to: %s", location)
|
||||
initUpdate()
|
||||
}
|
||||
|
||||
func main() {
|
||||
godotenv.Load(".env")
|
||||
go BotStart.Start()
|
||||
go scheduleTimetableUpdate()
|
||||
|
||||
scheduleTimetableUpdate()
|
||||
sigChan := make(chan os.Signal, 1)
|
||||
signal.Notify(sigChan, syscall.SIGINT, syscall.SIGTERM)
|
||||
|
||||
log.Println("Program is running. Press Ctrl+C to stop.")
|
||||
// Start logging
|
||||
// Run()
|
||||
// Block until we receive a signal
|
||||
<-sigChan
|
||||
log.Println("Shutting down...")
|
||||
}
|
||||
|
||||
func getTime() time.Time {
|
||||
return time.Now().In(location)
|
||||
}
|
||||
|
||||
func isScheduledTime(now time.Time) bool {
|
||||
scheduled := []string{"07:45", "08:35", "09:35", "10:25", "11:25", "12:15", "13:40", "14:25", "15:20", "16:00"}
|
||||
current := now.Format("15:04")
|
||||
|
|
@ -143,29 +126,9 @@ func isScheduledTime(now time.Time) bool {
|
|||
}
|
||||
|
||||
func initUpdate() {
|
||||
// Load all registered users
|
||||
accounts, err := BotStart.LoadAndDecryptAccounts()
|
||||
if err != nil {
|
||||
log.Printf("Error loading accounts: %v", err)
|
||||
}
|
||||
|
||||
// Add the default user from .env
|
||||
defaultUser := os.Getenv("UNTIS_USER")
|
||||
defaultPassword := os.Getenv("UNTIS_PASSWORD")
|
||||
if defaultUser != "" && defaultPassword != "" {
|
||||
accounts = append(accounts, BotStart.DecryptedAccount{
|
||||
UserID: "default",
|
||||
Username: defaultUser,
|
||||
DecryptedPassword: defaultPassword,
|
||||
})
|
||||
}
|
||||
|
||||
// Process each user
|
||||
for _, acc := range accounts {
|
||||
// Fetch the latest timetable and only timetable
|
||||
Untis.Main(acc.Username, acc.DecryptedPassword, acc.UserID)
|
||||
time.Sleep(3 * time.Second)
|
||||
}
|
||||
Untis.Main(defaultUser, defaultPassword, "default")
|
||||
}
|
||||
|
||||
func scheduleTimetableUpdate() {
|
||||
|
|
@ -178,7 +141,6 @@ func scheduleTimetableUpdate() {
|
|||
if err != nil {
|
||||
log.Printf("Error loading accounts: %v", err)
|
||||
}
|
||||
|
||||
// Add the default user from .env
|
||||
defaultUser := os.Getenv("UNTIS_USER")
|
||||
defaultPassword := os.Getenv("UNTIS_PASSWORD")
|
||||
|
|
@ -194,7 +156,6 @@ func scheduleTimetableUpdate() {
|
|||
for _, acc := range accounts {
|
||||
// Fetch the latest timetable and only timetable
|
||||
Untis.Update(acc.Username, acc.DecryptedPassword, acc.UserID)
|
||||
time.Sleep(3 * time.Second)
|
||||
|
||||
// Check for changes
|
||||
timetableFile := fmt.Sprintf("timetableFilled_%s.json", acc.UserID)
|
||||
|
|
@ -230,10 +191,10 @@ func scheduleTimetableUpdate() {
|
|||
prevTimeslotMap := make(map[string]NamedTimetableEntry)
|
||||
|
||||
// Get current date to filter out new day changes
|
||||
today := getTime().Format("02-01-2006")
|
||||
today := Untis.GetTime().Format("02-01-2006")
|
||||
// Get current time to filter any changes to Timetable before 3am so the new day changes stop
|
||||
//
|
||||
now := getTime()
|
||||
now := Untis.GetTime()
|
||||
// If before 1am stop and update userdata
|
||||
if now.Hour() < 1 {
|
||||
prevData[acc.UserID] = data
|
||||
|
|
@ -337,14 +298,11 @@ func scheduleTimetableUpdate() {
|
|||
sendUpdateDiscordWebhookWithDetails(changes)
|
||||
}
|
||||
}
|
||||
} else {
|
||||
// First run — no previous data, so don't notify
|
||||
log.Printf("First timetable fetch for user %s", acc.Username)
|
||||
}
|
||||
|
||||
// Always update prevData
|
||||
prevData[acc.UserID] = data
|
||||
}
|
||||
time.Sleep(3 * time.Second)
|
||||
}
|
||||
|
||||
// Initial update
|
||||
|
|
@ -360,7 +318,7 @@ func scheduleTimetableUpdate() {
|
|||
|
||||
// Ticker for scheduled lesson notifications
|
||||
startMinuteTicker(func() {
|
||||
now := getTime()
|
||||
now := Untis.GetTime()
|
||||
if isScheduledTime(now) {
|
||||
log.Println("Scheduled time reached, running notifications...")
|
||||
accounts, _ := BotStart.LoadAndDecryptAccounts()
|
||||
|
|
@ -372,10 +330,11 @@ func scheduleTimetableUpdate() {
|
|||
log.Println("Finished running notifications.")
|
||||
}
|
||||
})
|
||||
log.Println("Updated all users")
|
||||
}
|
||||
|
||||
func startMinuteTicker(f func()) {
|
||||
now := getTime()
|
||||
now := Untis.GetTime()
|
||||
next := now.Truncate(time.Minute).Add(time.Minute)
|
||||
time.Sleep(time.Until(next))
|
||||
ticker := time.NewTicker(1 * time.Minute)
|
||||
|
|
@ -404,7 +363,7 @@ func Run(userID string) {
|
|||
roomByStartTime, _ := MapTimeToRoom(timetableFile)
|
||||
subjectByStartTime, _ := MapTimeToSubject(timetableFile)
|
||||
|
||||
now := getTime().Format("15:04")
|
||||
now := Untis.GetTime().Format("15:04")
|
||||
|
||||
nextTime, room, foundRoom := NextRoomForTime(roomByStartTime, now)
|
||||
if !foundRoom {
|
||||
|
|
@ -653,7 +612,7 @@ func sendDiscordWebhook(subject string, room string, nextTime string, Status str
|
|||
if resp.StatusCode >= 200 && resp.StatusCode < 300 {
|
||||
log.Println("Discord webhook notification sent successfully")
|
||||
} else {
|
||||
body, _ := ioutil.ReadAll(resp.Body)
|
||||
body, _ := io.ReadAll(resp.Body)
|
||||
log.Printf("Discord webhook failed with status %d: %s", resp.StatusCode, string(body))
|
||||
}
|
||||
}
|
||||
|
|
@ -684,7 +643,7 @@ func sendUpdateDiscordWebhookWithDetails(changes []string) {
|
|||
if resp.StatusCode >= 200 && resp.StatusCode < 300 {
|
||||
log.Println("Detailed Discord webhook sent successfully")
|
||||
} else {
|
||||
body, _ := ioutil.ReadAll(resp.Body)
|
||||
body, _ := io.ReadAll(resp.Body)
|
||||
log.Printf("Discord webhook failed with status %d: %s", resp.StatusCode, string(body))
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in a new issue