-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
schedule scraping kinda works, added boilerplate
- Loading branch information
1 parent
76a59ec
commit b38b70a
Showing
30 changed files
with
2,242 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,15 @@ | ||
{ | ||
// Use IntelliSense to learn about possible attributes. | ||
// Hover to view descriptions of existing attributes. | ||
// For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387 | ||
"version": "0.2.0", | ||
"configurations": [ | ||
{ | ||
"name": "Launch Package", | ||
"type": "go", | ||
"request": "launch", | ||
"mode": "auto", | ||
"program": "${fileDirname}/main.go", | ||
} | ||
] | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,8 @@ | ||
{ | ||
"scraper": { | ||
"optivum_base_url": "https://zsem.edu.pl/plany/plany/", | ||
"division_endpoint": "o%d.html", | ||
"teacher_endpoint": "n%d.html", | ||
"room_endpoint": "s%d.html" | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,21 @@ | ||
// main.go | ||
package main | ||
|
||
import ( | ||
"fmt" | ||
|
||
"smuggr.xyz/optivum-bsf/common/config" | ||
"smuggr.xyz/optivum-bsf/core/scraper" | ||
) | ||
|
||
func main() { | ||
if err := config.Initialize(); err != nil { | ||
panic(err) | ||
} | ||
|
||
if err := scraper.Initialize(); err != nil { | ||
panic(err) | ||
} | ||
|
||
fmt.Println(scraper.ScrapeDivision(1)) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,51 @@ | ||
// config.go | ||
package config | ||
|
||
import ( | ||
"fmt" | ||
"os" | ||
|
||
"github.com/joho/godotenv" | ||
"github.com/spf13/viper" | ||
) | ||
|
||
var Global GlobalConfig | ||
|
||
func loadEnv() error { | ||
err := godotenv.Load() | ||
if err != nil { | ||
return err | ||
} | ||
|
||
return nil | ||
} | ||
|
||
func loadConfig(config *GlobalConfig) error { | ||
if err := viper.ReadInConfig(); err != nil { | ||
return err | ||
} | ||
|
||
err := viper.Unmarshal(config) | ||
if err != nil { | ||
return err | ||
} | ||
|
||
return nil | ||
} | ||
|
||
func Initialize() error { | ||
fmt.Println("initializing config...") | ||
|
||
if err := loadEnv(); err != nil { | ||
return err | ||
} | ||
|
||
viper.AddConfigPath(os.Getenv("CONFIG_PATH")) | ||
viper.SetConfigType(os.Getenv("CONFIG_TYPE")) | ||
|
||
if err := loadConfig(&Global); err != nil { | ||
return err | ||
} | ||
|
||
return nil | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,28 @@ | ||
// config/models.go | ||
package config | ||
|
||
type GeneralConfig struct { | ||
Debug bool `mapstructure:"debug"` | ||
SyncSchedule bool `mapstructure:"sync_schedule"` | ||
RelayOnDuration int `mapstructure:"relay_on_duration"` | ||
} | ||
|
||
type ScraperConfig struct { | ||
OptivumBaseUrl string `mapstructure:"optivum_base_url"` | ||
DivisionEndpoint string `mapstructure:"division_endpoint"` | ||
TeacherEndpoint string `mapstructure:"teacher_endpoint"` | ||
RoomEndpoint string `mapstructure:"room_endpoint"` | ||
} | ||
|
||
type DevicesConfig struct { | ||
DisplayAddress uint16 `mapstructure:"display_address"` | ||
RTCAddress uint16 `mapstructure:"rtc_address"` | ||
I2CBus string `mapstructure:"i2c_bus"` | ||
RelayPin string `mapstructure:"relay_pin"` | ||
} | ||
|
||
type GlobalConfig struct { | ||
General GeneralConfig `mapstructure:"general"` | ||
Scraper ScraperConfig `mapstructure:"scraper"` | ||
Devices DevicesConfig `mapstructure:"devices"` | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,61 @@ | ||
// utils.go | ||
package utils | ||
|
||
import ( | ||
"fmt" | ||
"net" | ||
"net/http" | ||
"strings" | ||
) | ||
|
||
func GetIP() (string, error) { | ||
interfaces, err := net.Interfaces() | ||
if err != nil { | ||
return "", err | ||
} | ||
|
||
for _, i := range interfaces { | ||
// Skip down or loopback interfaces | ||
if i.Flags&net.FlagUp == 0 || i.Flags&net.FlagLoopback != 0 { | ||
continue | ||
} | ||
|
||
addrs, err := i.Addrs() | ||
if err != nil { | ||
return "", err | ||
} | ||
|
||
for _, addr := range addrs { | ||
var ip net.IP | ||
switch v := addr.(type) { | ||
case *net.IPNet: | ||
ip = v.IP | ||
case *net.IPAddr: | ||
ip = v.IP | ||
} | ||
|
||
// Only return non-loopback IPv4 addresses | ||
if ip != nil && ip.To4() != nil { | ||
return ip.String(), nil | ||
} | ||
} | ||
} | ||
return "", fmt.Errorf("no valid IPv4 address found") | ||
} | ||
|
||
func CheckURL(url string) bool { | ||
resp, err := http.Get(url) | ||
if err != nil { | ||
return false | ||
} | ||
defer resp.Body.Close() | ||
|
||
return resp.StatusCode == http.StatusOK | ||
} | ||
|
||
func IsEmptyOrInvisible(text string) bool { | ||
text = strings.ReplaceAll(text, "\u00a0", " ") | ||
text = strings.TrimSpace(text) | ||
|
||
return text == "" | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,88 @@ | ||
// scraper/models.go | ||
package scraper | ||
|
||
import ( | ||
"fmt" | ||
"strconv" | ||
"strings" | ||
"time" | ||
) | ||
|
||
type TimeString string | ||
|
||
func (t TimeString) ToTimestamp() (Timestamp, error) { | ||
parts := strings.Split(string(t), ":") | ||
if len(parts) < 2 || len(parts) > 3 { | ||
return Timestamp{}, fmt.Errorf("invalid time format: %s", t) | ||
} | ||
|
||
hour, err := strconv.Atoi(parts[0]) | ||
if err != nil { | ||
return Timestamp{}, fmt.Errorf("invalid hour: %w", err) | ||
} | ||
|
||
minute, err := strconv.Atoi(parts[1]) | ||
if err != nil { | ||
return Timestamp{}, fmt.Errorf("invalid minute: %w", err) | ||
} | ||
|
||
return Timestamp{Hour: hour, Minute: minute}, nil | ||
} | ||
|
||
type Timestamp struct { | ||
Hour int `json:"h"` | ||
Minute int `json:"m"` | ||
} | ||
|
||
func (t Timestamp) String() string { | ||
return fmt.Sprintf("%02d:%02d", t.Hour, t.Minute) | ||
} | ||
|
||
func (t Timestamp) Compare(time time.Time) bool { | ||
return t.Hour == time.Hour() && t.Minute == time.Minute() | ||
} | ||
|
||
type TimeRange struct { | ||
Start Timestamp `json:"start"` | ||
End Timestamp `json:"end"` | ||
} | ||
|
||
func (tr TimeRange) String() string { | ||
return fmt.Sprintf("%s-%s", tr.Start, tr.End) | ||
} | ||
|
||
type Teacher struct { | ||
Designator string `json:"designator"` | ||
FullName string `json:"full_name"` | ||
Schedule Schedule `json:"schedule"` | ||
} | ||
|
||
type Room struct { | ||
Designator string `json:"designator"` | ||
FullName string `json:"full_name"` | ||
Schedule Schedule `json:"schedule"` | ||
BuildingName string `json:"building_name"` | ||
} | ||
|
||
type Lesson struct { | ||
FullName string `json:"full_name"` | ||
Teacher string `json:"teacher"` | ||
Room string `json:"room"` | ||
Division string `json:"division"` | ||
TimeRange TimeRange `json:"time_range"` | ||
} | ||
|
||
func (l Lesson) String() string { | ||
return fmt.Sprintf("[%s %s %s %s %s]", l.FullName, l.Teacher, l.Room, l.Division, l.TimeRange) | ||
} | ||
|
||
// Schedule is a 3D array of lessons, first dimension is day, | ||
// second is the lesson number, third are the lessons | ||
type Schedule [][][]Lesson | ||
|
||
type Division struct { | ||
Index uint `json:"index"` | ||
Designator string `json:"designator"` | ||
FullName string `json:"full_name"` | ||
Schedule Schedule `json:"schedule"` | ||
} |
Oops, something went wrong.