basic app
This commit is contained in:
parent
1892d3d83e
commit
e95ab1fb73
3
.gitignore
vendored
3
.gitignore
vendored
@ -7,6 +7,7 @@
|
|||||||
*.dll
|
*.dll
|
||||||
*.so
|
*.so
|
||||||
*.dylib
|
*.dylib
|
||||||
|
**.db
|
||||||
|
|
||||||
# Test binary, built with `go test -c`
|
# Test binary, built with `go test -c`
|
||||||
*.test
|
*.test
|
||||||
@ -29,4 +30,4 @@ go.work.sum
|
|||||||
|
|
||||||
# Editor/IDE
|
# Editor/IDE
|
||||||
# .idea/
|
# .idea/
|
||||||
# .vscode/
|
.vscode/
|
||||||
|
|||||||
114
app/backend/binary.go
Normal file
114
app/backend/binary.go
Normal file
@ -0,0 +1,114 @@
|
|||||||
|
package backend
|
||||||
|
|
||||||
|
import (
|
||||||
|
"binaryserver/app/db"
|
||||||
|
"fmt"
|
||||||
|
"net/http"
|
||||||
|
"strconv"
|
||||||
|
"strings"
|
||||||
|
|
||||||
|
"github.com/go-rod/rod"
|
||||||
|
"github.com/go-rod/rod/lib/launcher"
|
||||||
|
)
|
||||||
|
|
||||||
|
var browser *rod.Browser
|
||||||
|
|
||||||
|
func asciiToBinary(text string) string {
|
||||||
|
var result []string
|
||||||
|
for _, char := range text {
|
||||||
|
binary := fmt.Sprintf("%08b", char) // 8-bit binary format
|
||||||
|
result = append(result, binary)
|
||||||
|
}
|
||||||
|
return strings.Join(result, " ")
|
||||||
|
}
|
||||||
|
|
||||||
|
func binaryToASCII(binary string) (string, error) {
|
||||||
|
// Ensure the length of the binary string is a multiple of 8
|
||||||
|
if len(binary)%8 != 0 {
|
||||||
|
return "", fmt.Errorf("binary string length must be a multiple of 8")
|
||||||
|
}
|
||||||
|
|
||||||
|
var sb strings.Builder
|
||||||
|
for i := 0; i < len(binary); i += 8 {
|
||||||
|
byteStr := binary[i : i+8]
|
||||||
|
b, err := strconv.ParseUint(byteStr, 2, 8)
|
||||||
|
if err != nil {
|
||||||
|
return "", fmt.Errorf("invalid binary sequence at position %d: %v", i, err)
|
||||||
|
}
|
||||||
|
sb.WriteByte(byte(b))
|
||||||
|
}
|
||||||
|
return sb.String(), nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func instagramHandleExists(username string, bypass ...bool) string {
|
||||||
|
records, _ := db.GetRecords(db.QueryOptions{Where: fmt.Sprintf(`handle='%v'`, username)})
|
||||||
|
if len(records) > 0 && len(bypass) == 0 {
|
||||||
|
return records[0].URL
|
||||||
|
}
|
||||||
|
url := fmt.Sprintf("https://www.instagram.com/%s/", username)
|
||||||
|
|
||||||
|
page := browser.MustPage(url)
|
||||||
|
|
||||||
|
// Wait until body is loaded
|
||||||
|
page.MustWaitLoad().MustWaitIdle()
|
||||||
|
|
||||||
|
body := page.MustElement("body").MustText()
|
||||||
|
|
||||||
|
record := db.NewRecord(username, url)
|
||||||
|
|
||||||
|
// Instagram shows this for non-existent users
|
||||||
|
if strings.Contains(body, "Sorry, this page isn't available") {
|
||||||
|
record.URL = ""
|
||||||
|
db.SaveRecord(record)
|
||||||
|
return ""
|
||||||
|
}
|
||||||
|
db.SaveRecord(record)
|
||||||
|
return url
|
||||||
|
}
|
||||||
|
|
||||||
|
func BinaryHandler(w http.ResponseWriter, req *http.Request) {
|
||||||
|
binaryInput := strings.ReplaceAll(req.URL.Query().Get("binary"), " ", "")
|
||||||
|
var text string
|
||||||
|
var handle string
|
||||||
|
var err error
|
||||||
|
if binaryInput == "" {
|
||||||
|
asciiInput := req.URL.Query().Get("text")
|
||||||
|
if asciiInput == "" {
|
||||||
|
fmt.Fprintf(w, "Could not encode or decode!\n")
|
||||||
|
return
|
||||||
|
}
|
||||||
|
text = asciiToBinary(asciiInput)
|
||||||
|
fmt.Fprintf(w, "%v\n", GetFancyResponse(`<center><p>`+text+`</p></center>`, ""))
|
||||||
|
return
|
||||||
|
} else {
|
||||||
|
text, err = binaryToASCII(binaryInput)
|
||||||
|
text = strings.ReplaceAll(text, "@", "")
|
||||||
|
handle = text
|
||||||
|
}
|
||||||
|
|
||||||
|
if err != nil {
|
||||||
|
fmt.Fprintf(w, "Could not decode!\n")
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
var url string
|
||||||
|
if url = instagramHandleExists(text); url != "" {
|
||||||
|
text = `<center><a href="` + url + `">` + text + `</a></center>`
|
||||||
|
} else {
|
||||||
|
text = `<center><p>` + text + `</p></center>`
|
||||||
|
}
|
||||||
|
if url == "" {
|
||||||
|
handle = ""
|
||||||
|
}
|
||||||
|
|
||||||
|
fmt.Fprintf(w, "%v\n", GetFancyResponse(text, handle))
|
||||||
|
}
|
||||||
|
|
||||||
|
func init() {
|
||||||
|
path, _ := launcher.New().
|
||||||
|
Headless(true).
|
||||||
|
// Uncomment below to see browser
|
||||||
|
// Set("headless", "false").
|
||||||
|
Launch()
|
||||||
|
browser = rod.New().ControlURL(path).MustConnect()
|
||||||
|
}
|
||||||
51
app/backend/page.go
Normal file
51
app/backend/page.go
Normal file
@ -0,0 +1,51 @@
|
|||||||
|
package backend
|
||||||
|
|
||||||
|
func GetFancyResponse(input, handle string) string {
|
||||||
|
var hasHandle string
|
||||||
|
if handle != "" {
|
||||||
|
hasHandle = `<a class="bottom-right" href="/report?handle=` + handle + `">Report Broken Link</a>`
|
||||||
|
}
|
||||||
|
return `
|
||||||
|
<!DOCTYPE html>
|
||||||
|
<html lang="en">
|
||||||
|
<head>
|
||||||
|
<meta charset="UTF-8">
|
||||||
|
<meta name="viewport" content="width=device-width, initial-scale=1.0">
|
||||||
|
<title>Decoded Binary</title>
|
||||||
|
<style>
|
||||||
|
body {
|
||||||
|
font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
|
||||||
|
background-color:rgb(19, 31, 49);
|
||||||
|
margin: 40px;
|
||||||
|
color: #333;
|
||||||
|
}
|
||||||
|
.fancy-box {
|
||||||
|
background-color: #000000;
|
||||||
|
border: 2px solid #4a90e2;
|
||||||
|
border-radius: 12px;
|
||||||
|
box-shadow: 0 8px 20px rgba(0, 0, 0, 0.1);
|
||||||
|
padding: 30px;
|
||||||
|
max-width: 600px;
|
||||||
|
margin: 0 auto;
|
||||||
|
}
|
||||||
|
.bottom-right {
|
||||||
|
position: absolute;
|
||||||
|
bottom: 10px;
|
||||||
|
right: 10px;
|
||||||
|
margin: 0;
|
||||||
|
}
|
||||||
|
p {
|
||||||
|
color: #ffffff;
|
||||||
|
font-size: 1.1em;
|
||||||
|
}
|
||||||
|
</style>
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
<div class="fancy-box">
|
||||||
|
` + input + `
|
||||||
|
` + hasHandle + `
|
||||||
|
</div>
|
||||||
|
</body>
|
||||||
|
</html>
|
||||||
|
`
|
||||||
|
}
|
||||||
20
app/backend/report.go
Normal file
20
app/backend/report.go
Normal file
@ -0,0 +1,20 @@
|
|||||||
|
package backend
|
||||||
|
|
||||||
|
import (
|
||||||
|
"binaryserver/app/db"
|
||||||
|
"fmt"
|
||||||
|
"net/http"
|
||||||
|
)
|
||||||
|
|
||||||
|
func ReportHandler(w http.ResponseWriter, req *http.Request) {
|
||||||
|
handle := req.URL.Query().Get("handle")
|
||||||
|
records, _ := db.GetRecords(db.QueryOptions{Where: fmt.Sprintf(`handle='%v'`, handle)})
|
||||||
|
if len(records) > 0 {
|
||||||
|
if result := instagramHandleExists(records[0].Handle, true); result == "" && records[0].URL != "" {
|
||||||
|
fmt.Fprintf(w, "Link does seem to be bad. Fixing...\n")
|
||||||
|
db.DeleteRecord(records[0])
|
||||||
|
} else {
|
||||||
|
fmt.Fprintf(w, "Link seems to be active and working!\n")
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
39
app/db/db.go
Normal file
39
app/db/db.go
Normal file
@ -0,0 +1,39 @@
|
|||||||
|
package db
|
||||||
|
|
||||||
|
import (
|
||||||
|
"database/sql"
|
||||||
|
|
||||||
|
_ "modernc.org/sqlite"
|
||||||
|
)
|
||||||
|
|
||||||
|
var conn *sql.DB
|
||||||
|
|
||||||
|
func HandleConn(testing ...bool) *sql.DB {
|
||||||
|
if len(testing) > 0 {
|
||||||
|
conn, _ = sql.Open("sqlite", "file::memory:?cache=shared")
|
||||||
|
buildSchema()
|
||||||
|
return conn
|
||||||
|
}
|
||||||
|
if conn == nil {
|
||||||
|
conn, _ = sql.Open("sqlite", "records.db")
|
||||||
|
buildSchema()
|
||||||
|
return conn
|
||||||
|
}
|
||||||
|
return conn
|
||||||
|
}
|
||||||
|
|
||||||
|
func buildSchema() error {
|
||||||
|
c := HandleConn()
|
||||||
|
_, err := c.Exec(`
|
||||||
|
|
||||||
|
CREATE TABLE IF NOT EXISTS records
|
||||||
|
(
|
||||||
|
UUID TEXT NOT NULL,
|
||||||
|
Handle TEXT NOT NULL UNIQUE,
|
||||||
|
URL TEXT NOT NULL,
|
||||||
|
PRIMARY KEY (UUID)
|
||||||
|
);
|
||||||
|
|
||||||
|
`)
|
||||||
|
return err
|
||||||
|
}
|
||||||
77
app/db/record.go
Normal file
77
app/db/record.go
Normal file
@ -0,0 +1,77 @@
|
|||||||
|
package db
|
||||||
|
|
||||||
|
import (
|
||||||
|
"binaryserver/app/utils"
|
||||||
|
|
||||||
|
"github.com/google/uuid"
|
||||||
|
)
|
||||||
|
|
||||||
|
type Record struct {
|
||||||
|
UUID uuid.UUID `json:"uuid"`
|
||||||
|
Handle string `json:"handle"`
|
||||||
|
URL string `json:"url"`
|
||||||
|
}
|
||||||
|
|
||||||
|
func NewRecord(handle, url string) Record {
|
||||||
|
return Record{
|
||||||
|
UUID: utils.GetUUID(),
|
||||||
|
Handle: handle,
|
||||||
|
URL: url,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func SaveRecord(record Record) error {
|
||||||
|
conn := HandleConn()
|
||||||
|
stmt, err := conn.Prepare(`INSERT INTO records
|
||||||
|
VALUES(?, ?, ?)`)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
_, err = stmt.Exec(record.UUID.String(), record.Handle, record.URL)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
defer stmt.Close()
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func GetRecords(opts QueryOptions) ([]Record, error) {
|
||||||
|
conn := HandleConn()
|
||||||
|
var records []Record
|
||||||
|
stmt, err := opts.Build(conn, "records")
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
row, err := stmt.Query()
|
||||||
|
stmt.Close()
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
defer row.Close()
|
||||||
|
for {
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
if !row.Next() {
|
||||||
|
break
|
||||||
|
}
|
||||||
|
record := Record{}
|
||||||
|
row.Scan(&record.UUID, &record.Handle, &record.URL)
|
||||||
|
records = append(records, record)
|
||||||
|
}
|
||||||
|
return records, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func DeleteRecord(record Record) error {
|
||||||
|
stmt, err := conn.Prepare(`DELETE FROM records
|
||||||
|
WHERE UUID = ?`)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
defer stmt.Close()
|
||||||
|
_, err = stmt.Exec(record.UUID.String())
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
18
app/db/record_test.go
Normal file
18
app/db/record_test.go
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
package db
|
||||||
|
|
||||||
|
import (
|
||||||
|
"testing"
|
||||||
|
|
||||||
|
"github.com/stretchr/testify/assert"
|
||||||
|
)
|
||||||
|
|
||||||
|
func TestRecords(t *testing.T) {
|
||||||
|
HandleConn(true)
|
||||||
|
rec := NewRecord("test", "https://instagram.com/handle")
|
||||||
|
err := SaveRecord(rec)
|
||||||
|
assert.Nil(t, err)
|
||||||
|
records, err := GetRecords(QueryOptions{Where: `handle='test'`})
|
||||||
|
assert.Nil(t, err)
|
||||||
|
assert.Greater(t, len(records), 0)
|
||||||
|
assert.Equal(t, "https://instagram.com/handle", records[0].URL)
|
||||||
|
}
|
||||||
50
app/db/types.go
Normal file
50
app/db/types.go
Normal file
@ -0,0 +1,50 @@
|
|||||||
|
package db
|
||||||
|
|
||||||
|
import (
|
||||||
|
"database/sql"
|
||||||
|
"fmt"
|
||||||
|
"strings"
|
||||||
|
)
|
||||||
|
|
||||||
|
type QueryOptions struct {
|
||||||
|
Select []string
|
||||||
|
Where string
|
||||||
|
OrderBy string
|
||||||
|
Limit uint
|
||||||
|
Offset uint
|
||||||
|
}
|
||||||
|
|
||||||
|
func (o *QueryOptions) Build(conn *sql.DB, table string) (*sql.Stmt, error) {
|
||||||
|
sel := "*"
|
||||||
|
where := ""
|
||||||
|
orderby := ""
|
||||||
|
limit := ""
|
||||||
|
if o.Select != nil {
|
||||||
|
sel = strings.Join(o.Select, ", ")
|
||||||
|
}
|
||||||
|
if o.Where != "" {
|
||||||
|
where = fmt.Sprintf(
|
||||||
|
`WHERE
|
||||||
|
%v`, o.Where)
|
||||||
|
}
|
||||||
|
if o.OrderBy != "" {
|
||||||
|
orderby = fmt.Sprintf(
|
||||||
|
`ORDER BY
|
||||||
|
%v`, o.OrderBy)
|
||||||
|
}
|
||||||
|
if o.Limit != 0 && o.Offset != 0 {
|
||||||
|
limit = fmt.Sprintf(
|
||||||
|
`LIMIT %v OFFSET %v;`, o.Limit, o.Offset)
|
||||||
|
} else if o.Limit != 0 {
|
||||||
|
limit = fmt.Sprintf(
|
||||||
|
`LIMIT %v`, o.Limit)
|
||||||
|
}
|
||||||
|
return conn.Prepare(fmt.Sprintf(
|
||||||
|
`SELECT
|
||||||
|
%v
|
||||||
|
FROM
|
||||||
|
%v
|
||||||
|
%v
|
||||||
|
%v
|
||||||
|
%v;`, sel, table, where, orderby, limit))
|
||||||
|
}
|
||||||
12
app/utils/utils.go
Normal file
12
app/utils/utils.go
Normal file
@ -0,0 +1,12 @@
|
|||||||
|
package utils
|
||||||
|
|
||||||
|
import "github.com/google/uuid"
|
||||||
|
|
||||||
|
func GetUUID() uuid.UUID {
|
||||||
|
uuid.SetClockSequence(uuid.ClockSequence())
|
||||||
|
if uid, err := uuid.NewV7(); err == nil {
|
||||||
|
return uid
|
||||||
|
}
|
||||||
|
uid, _ := uuid.NewUUID()
|
||||||
|
return uid
|
||||||
|
}
|
||||||
31
go.mod
Normal file
31
go.mod
Normal file
@ -0,0 +1,31 @@
|
|||||||
|
module binaryserver
|
||||||
|
|
||||||
|
go 1.24.2
|
||||||
|
|
||||||
|
require (
|
||||||
|
github.com/go-rod/rod v0.116.2
|
||||||
|
github.com/google/uuid v1.6.0
|
||||||
|
github.com/patrickmn/go-cache v2.1.0+incompatible
|
||||||
|
github.com/stretchr/testify v1.10.0
|
||||||
|
modernc.org/sqlite v1.38.0
|
||||||
|
)
|
||||||
|
|
||||||
|
require (
|
||||||
|
github.com/davecgh/go-spew v1.1.1 // indirect
|
||||||
|
github.com/dustin/go-humanize v1.0.1 // indirect
|
||||||
|
github.com/mattn/go-isatty v0.0.20 // indirect
|
||||||
|
github.com/ncruces/go-strftime v0.1.9 // indirect
|
||||||
|
github.com/pmezard/go-difflib v1.0.0 // indirect
|
||||||
|
github.com/remyoudompheng/bigfft v0.0.0-20230129092748-24d4a6f8daec // indirect
|
||||||
|
github.com/ysmood/fetchup v0.2.3 // indirect
|
||||||
|
github.com/ysmood/goob v0.4.0 // indirect
|
||||||
|
github.com/ysmood/got v0.40.0 // indirect
|
||||||
|
github.com/ysmood/gson v0.7.3 // indirect
|
||||||
|
github.com/ysmood/leakless v0.9.0 // indirect
|
||||||
|
golang.org/x/exp v0.0.0-20250408133849-7e4ce0ab07d0 // indirect
|
||||||
|
golang.org/x/sys v0.33.0 // indirect
|
||||||
|
gopkg.in/yaml.v3 v3.0.1 // indirect
|
||||||
|
modernc.org/libc v1.65.10 // indirect
|
||||||
|
modernc.org/mathutil v1.7.1 // indirect
|
||||||
|
modernc.org/memory v1.11.0 // indirect
|
||||||
|
)
|
||||||
75
go.sum
Normal file
75
go.sum
Normal file
@ -0,0 +1,75 @@
|
|||||||
|
github.com/davecgh/go-spew v1.1.1 h1:vj9j/u1bqnvCEfJOwUhtlOARqs3+rkHYY13jYWTU97c=
|
||||||
|
github.com/davecgh/go-spew v1.1.1/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
|
||||||
|
github.com/dustin/go-humanize v1.0.1 h1:GzkhY7T5VNhEkwH0PVJgjz+fX1rhBrR7pRT3mDkpeCY=
|
||||||
|
github.com/dustin/go-humanize v1.0.1/go.mod h1:Mu1zIs6XwVuF/gI1OepvI0qD18qycQx+mFykh5fBlto=
|
||||||
|
github.com/go-rod/rod v0.116.2 h1:A5t2Ky2A+5eD/ZJQr1EfsQSe5rms5Xof/qj296e+ZqA=
|
||||||
|
github.com/go-rod/rod v0.116.2/go.mod h1:H+CMO9SCNc2TJ2WfrG+pKhITz57uGNYU43qYHh438Mg=
|
||||||
|
github.com/google/pprof v0.0.0-20250317173921-a4b03ec1a45e h1:ijClszYn+mADRFY17kjQEVQ1XRhq2/JR1M3sGqeJoxs=
|
||||||
|
github.com/google/pprof v0.0.0-20250317173921-a4b03ec1a45e/go.mod h1:boTsfXsheKC2y+lKOCMpSfarhxDeIzfZG1jqGcPl3cA=
|
||||||
|
github.com/google/uuid v1.6.0 h1:NIvaJDMOsjHA8n1jAhLSgzrAzy1Hgr+hNrb57e+94F0=
|
||||||
|
github.com/google/uuid v1.6.0/go.mod h1:TIyPZe4MgqvfeYDBFedMoGGpEw/LqOeaOT+nhxU+yHo=
|
||||||
|
github.com/mattn/go-isatty v0.0.20 h1:xfD0iDuEKnDkl03q4limB+vH+GxLEtL/jb4xVJSWWEY=
|
||||||
|
github.com/mattn/go-isatty v0.0.20/go.mod h1:W+V8PltTTMOvKvAeJH7IuucS94S2C6jfK/D7dTCTo3Y=
|
||||||
|
github.com/ncruces/go-strftime v0.1.9 h1:bY0MQC28UADQmHmaF5dgpLmImcShSi2kHU9XLdhx/f4=
|
||||||
|
github.com/ncruces/go-strftime v0.1.9/go.mod h1:Fwc5htZGVVkseilnfgOVb9mKy6w1naJmn9CehxcKcls=
|
||||||
|
github.com/patrickmn/go-cache v2.1.0+incompatible h1:HRMgzkcYKYpi3C8ajMPV8OFXaaRUnok+kx1WdO15EQc=
|
||||||
|
github.com/patrickmn/go-cache v2.1.0+incompatible/go.mod h1:3Qf8kWWT7OJRJbdiICTKqZju1ZixQ/KpMGzzAfe6+WQ=
|
||||||
|
github.com/pmezard/go-difflib v1.0.0 h1:4DBwDE0NGyQoBHbLQYPwSUPoCMWR5BEzIk/f1lZbAQM=
|
||||||
|
github.com/pmezard/go-difflib v1.0.0/go.mod h1:iKH77koFhYxTK1pcRnkKkqfTogsbg7gZNVY4sRDYZ/4=
|
||||||
|
github.com/remyoudompheng/bigfft v0.0.0-20230129092748-24d4a6f8daec h1:W09IVJc94icq4NjY3clb7Lk8O1qJ8BdBEF8z0ibU0rE=
|
||||||
|
github.com/remyoudompheng/bigfft v0.0.0-20230129092748-24d4a6f8daec/go.mod h1:qqbHyh8v60DhA7CoWK5oRCqLrMHRGoxYCSS9EjAz6Eo=
|
||||||
|
github.com/stretchr/testify v1.10.0 h1:Xv5erBjTwe/5IxqUQTdXv5kgmIvbHo3QQyRwhJsOfJA=
|
||||||
|
github.com/stretchr/testify v1.10.0/go.mod h1:r2ic/lqez/lEtzL7wO/rwa5dbSLXVDPFyf8C91i36aY=
|
||||||
|
github.com/ysmood/fetchup v0.2.3 h1:ulX+SonA0Vma5zUFXtv52Kzip/xe7aj4vqT5AJwQ+ZQ=
|
||||||
|
github.com/ysmood/fetchup v0.2.3/go.mod h1:xhibcRKziSvol0H1/pj33dnKrYyI2ebIvz5cOOkYGns=
|
||||||
|
github.com/ysmood/goob v0.4.0 h1:HsxXhyLBeGzWXnqVKtmT9qM7EuVs/XOgkX7T6r1o1AQ=
|
||||||
|
github.com/ysmood/goob v0.4.0/go.mod h1:u6yx7ZhS4Exf2MwciFr6nIM8knHQIE22lFpWHnfql18=
|
||||||
|
github.com/ysmood/gop v0.2.0 h1:+tFrG0TWPxT6p9ZaZs+VY+opCvHU8/3Fk6BaNv6kqKg=
|
||||||
|
github.com/ysmood/gop v0.2.0/go.mod h1:rr5z2z27oGEbyB787hpEcx4ab8cCiPnKxn0SUHt6xzk=
|
||||||
|
github.com/ysmood/got v0.40.0 h1:ZQk1B55zIvS7zflRrkGfPDrPG3d7+JOza1ZkNxcc74Q=
|
||||||
|
github.com/ysmood/got v0.40.0/go.mod h1:W7DdpuX6skL3NszLmAsC5hT7JAhuLZhByVzHTq874Qg=
|
||||||
|
github.com/ysmood/gotrace v0.6.0 h1:SyI1d4jclswLhg7SWTL6os3L1WOKeNn/ZtzVQF8QmdY=
|
||||||
|
github.com/ysmood/gotrace v0.6.0/go.mod h1:TzhIG7nHDry5//eYZDYcTzuJLYQIkykJzCRIo4/dzQM=
|
||||||
|
github.com/ysmood/gson v0.7.3 h1:QFkWbTH8MxyUTKPkVWAENJhxqdBa4lYTQWqZCiLG6kE=
|
||||||
|
github.com/ysmood/gson v0.7.3/go.mod h1:3Kzs5zDl21g5F/BlLTNcuAGAYLKt2lV5G8D1zF3RNmg=
|
||||||
|
github.com/ysmood/leakless v0.9.0 h1:qxCG5VirSBvmi3uynXFkcnLMzkphdh3xx5FtrORwDCU=
|
||||||
|
github.com/ysmood/leakless v0.9.0/go.mod h1:R8iAXPRaG97QJwqxs74RdwzcRHT1SWCGTNqY8q0JvMQ=
|
||||||
|
golang.org/x/exp v0.0.0-20250408133849-7e4ce0ab07d0 h1:R84qjqJb5nVJMxqWYb3np9L5ZsaDtB+a39EqjV0JSUM=
|
||||||
|
golang.org/x/exp v0.0.0-20250408133849-7e4ce0ab07d0/go.mod h1:S9Xr4PYopiDyqSyp5NjCrhFrqg6A5zA2E/iPHPhqnS8=
|
||||||
|
golang.org/x/mod v0.24.0 h1:ZfthKaKaT4NrhGVZHO1/WDTwGES4De8KtWO0SIbNJMU=
|
||||||
|
golang.org/x/mod v0.24.0/go.mod h1:IXM97Txy2VM4PJ3gI61r1YEk/gAj6zAHN3AdZt6S9Ww=
|
||||||
|
golang.org/x/sync v0.14.0 h1:woo0S4Yywslg6hp4eUFjTVOyKt0RookbpAHG4c1HmhQ=
|
||||||
|
golang.org/x/sync v0.14.0/go.mod h1:1dzgHSNfp02xaA81J2MS99Qcpr2w7fw1gpm99rleRqA=
|
||||||
|
golang.org/x/sys v0.6.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg=
|
||||||
|
golang.org/x/sys v0.33.0 h1:q3i8TbbEz+JRD9ywIRlyRAQbM0qF7hu24q3teo2hbuw=
|
||||||
|
golang.org/x/sys v0.33.0/go.mod h1:BJP2sWEmIv4KK5OTEluFJCKSidICx8ciO85XgH3Ak8k=
|
||||||
|
golang.org/x/tools v0.33.0 h1:4qz2S3zmRxbGIhDIAgjxvFutSvH5EfnsYrRBj0UI0bc=
|
||||||
|
golang.org/x/tools v0.33.0/go.mod h1:CIJMaWEY88juyUfo7UbgPqbC8rU2OqfAV1h2Qp0oMYI=
|
||||||
|
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM=
|
||||||
|
gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0=
|
||||||
|
gopkg.in/yaml.v3 v3.0.1 h1:fxVm/GzAzEWqLHuvctI91KS9hhNmmWOoWu0XTYJS7CA=
|
||||||
|
gopkg.in/yaml.v3 v3.0.1/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM=
|
||||||
|
modernc.org/cc/v4 v4.26.1 h1:+X5NtzVBn0KgsBCBe+xkDC7twLb/jNVj9FPgiwSQO3s=
|
||||||
|
modernc.org/cc/v4 v4.26.1/go.mod h1:uVtb5OGqUKpoLWhqwNQo/8LwvoiEBLvZXIQ/SmO6mL0=
|
||||||
|
modernc.org/ccgo/v4 v4.28.0 h1:rjznn6WWehKq7dG4JtLRKxb52Ecv8OUGah8+Z/SfpNU=
|
||||||
|
modernc.org/ccgo/v4 v4.28.0/go.mod h1:JygV3+9AV6SmPhDasu4JgquwU81XAKLd3OKTUDNOiKE=
|
||||||
|
modernc.org/fileutil v1.3.3 h1:3qaU+7f7xxTUmvU1pJTZiDLAIoJVdUSSauJNHg9yXoA=
|
||||||
|
modernc.org/fileutil v1.3.3/go.mod h1:HxmghZSZVAz/LXcMNwZPA/DRrQZEVP9VX0V4LQGQFOc=
|
||||||
|
modernc.org/gc/v2 v2.6.5 h1:nyqdV8q46KvTpZlsw66kWqwXRHdjIlJOhG6kxiV/9xI=
|
||||||
|
modernc.org/gc/v2 v2.6.5/go.mod h1:YgIahr1ypgfe7chRuJi2gD7DBQiKSLMPgBQe9oIiito=
|
||||||
|
modernc.org/libc v1.65.10 h1:ZwEk8+jhW7qBjHIT+wd0d9VjitRyQef9BnzlzGwMODc=
|
||||||
|
modernc.org/libc v1.65.10/go.mod h1:StFvYpx7i/mXtBAfVOjaU0PWZOvIRoZSgXhrwXzr8Po=
|
||||||
|
modernc.org/mathutil v1.7.1 h1:GCZVGXdaN8gTqB1Mf/usp1Y/hSqgI2vAGGP4jZMCxOU=
|
||||||
|
modernc.org/mathutil v1.7.1/go.mod h1:4p5IwJITfppl0G4sUEDtCr4DthTaT47/N3aT6MhfgJg=
|
||||||
|
modernc.org/memory v1.11.0 h1:o4QC8aMQzmcwCK3t3Ux/ZHmwFPzE6hf2Y5LbkRs+hbI=
|
||||||
|
modernc.org/memory v1.11.0/go.mod h1:/JP4VbVC+K5sU2wZi9bHoq2MAkCnrt2r98UGeSK7Mjw=
|
||||||
|
modernc.org/opt v0.1.4 h1:2kNGMRiUjrp4LcaPuLY2PzUfqM/w9N23quVwhKt5Qm8=
|
||||||
|
modernc.org/opt v0.1.4/go.mod h1:03fq9lsNfvkYSfxrfUhZCWPk1lm4cq4N+Bh//bEtgns=
|
||||||
|
modernc.org/sortutil v1.2.1 h1:+xyoGf15mM3NMlPDnFqrteY07klSFxLElE2PVuWIJ7w=
|
||||||
|
modernc.org/sortutil v1.2.1/go.mod h1:7ZI3a3REbai7gzCLcotuw9AC4VZVpYMjDzETGsSMqJE=
|
||||||
|
modernc.org/sqlite v1.38.0 h1:+4OrfPQ8pxHKuWG4md1JpR/EYAh3Md7TdejuuzE7EUI=
|
||||||
|
modernc.org/sqlite v1.38.0/go.mod h1:1Bj+yES4SVvBZ4cBOpVZ6QgesMCKpJZDq0nxYzOpmNE=
|
||||||
|
modernc.org/strutil v1.2.1 h1:UneZBkQA+DX2Rp35KcM69cSsNES9ly8mQWD71HKlOA0=
|
||||||
|
modernc.org/strutil v1.2.1/go.mod h1:EHkiggD70koQxjVdSBM3JKM7k6L0FbGE5eymy9i3B9A=
|
||||||
|
modernc.org/token v1.1.0 h1:Xl7Ap9dKaEs5kLoOQeQmPWevfnk/DM5qcLcYlA8ys6Y=
|
||||||
|
modernc.org/token v1.1.0/go.mod h1:UGzOrNV1mAFSEB63lOFHIpNRUVMvYTc6yu1SMY/XTDM=
|
||||||
Loading…
x
Reference in New Issue
Block a user