mirror of
https://git.maid.zone/stuff/soundcloak.git
synced 2025-12-11 06:09:38 +05:00
show user reposts; show track count in playlist meta; tidy templates; upd deps (templ)
This commit is contained in:
3
.gitignore
vendored
3
.gitignore
vendored
@@ -4,4 +4,5 @@ package-lock.json
|
|||||||
*_templ.go
|
*_templ.go
|
||||||
fly.toml
|
fly.toml
|
||||||
*.fiber.gz
|
*.fiber.gz
|
||||||
soundcloak.json
|
soundcloak.json
|
||||||
|
Dockerfile
|
||||||
@@ -111,6 +111,9 @@ input:focus {
|
|||||||
color: var(--accent);
|
color: var(--accent);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
.listing > .meta > p {
|
||||||
|
margin: 0;
|
||||||
|
}
|
||||||
|
|
||||||
details {
|
details {
|
||||||
border-color: var(--0);
|
border-color: var(--0);
|
||||||
|
|||||||
2
go.mod
2
go.mod
@@ -3,7 +3,7 @@ module github.com/maid-zone/soundcloak
|
|||||||
go 1.21.3
|
go 1.21.3
|
||||||
|
|
||||||
require (
|
require (
|
||||||
github.com/a-h/templ v0.2.778
|
github.com/a-h/templ v0.2.793
|
||||||
github.com/gofiber/fiber/v2 v2.52.5
|
github.com/gofiber/fiber/v2 v2.52.5
|
||||||
github.com/json-iterator/go v1.1.12
|
github.com/json-iterator/go v1.1.12
|
||||||
github.com/valyala/fasthttp v1.57.0
|
github.com/valyala/fasthttp v1.57.0
|
||||||
|
|||||||
2
go.sum
2
go.sum
@@ -1,5 +1,7 @@
|
|||||||
github.com/a-h/templ v0.2.778 h1:VzhOuvWECrwOec4790lcLlZpP4Iptt5Q4K9aFxQmtaM=
|
github.com/a-h/templ v0.2.778 h1:VzhOuvWECrwOec4790lcLlZpP4Iptt5Q4K9aFxQmtaM=
|
||||||
github.com/a-h/templ v0.2.778/go.mod h1:lq48JXoUvuQrU0VThrK31yFwdRjTCnIE5bcPCM9IP1w=
|
github.com/a-h/templ v0.2.778/go.mod h1:lq48JXoUvuQrU0VThrK31yFwdRjTCnIE5bcPCM9IP1w=
|
||||||
|
github.com/a-h/templ v0.2.793 h1:Io+/ocnfGWYO4VHdR0zBbf39PQlnzVCVVD+wEEs6/qY=
|
||||||
|
github.com/a-h/templ v0.2.793/go.mod h1:lq48JXoUvuQrU0VThrK31yFwdRjTCnIE5bcPCM9IP1w=
|
||||||
github.com/andybalholm/brotli v1.1.1 h1:PR2pgnyFznKEugtsUo0xLdDop5SKXd5Qf5ysW+7XdTA=
|
github.com/andybalholm/brotli v1.1.1 h1:PR2pgnyFznKEugtsUo0xLdDop5SKXd5Qf5ysW+7XdTA=
|
||||||
github.com/andybalholm/brotli v1.1.1/go.mod h1:05ib4cKhjx3OQYUY22hTVd34Bc8upXjOLL2rKwwZBoA=
|
github.com/andybalholm/brotli v1.1.1/go.mod h1:05ib4cKhjx3OQYUY22hTVd34Bc8upXjOLL2rKwwZBoA=
|
||||||
github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
|
github.com/davecgh/go-spew v1.1.0/go.mod h1:J7Y8YcW2NihsgmVo/mv3lAwl/skON4iLHjSsI+c5H38=
|
||||||
|
|||||||
@@ -33,6 +33,36 @@ type User struct {
|
|||||||
Verified bool `json:"verified"`
|
Verified bool `json:"verified"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
type RepostType string
|
||||||
|
|
||||||
|
const (
|
||||||
|
TrackRepost RepostType = "track-repost"
|
||||||
|
PlaylistRepost RepostType = "playlist-repost"
|
||||||
|
)
|
||||||
|
|
||||||
|
// not worthy of its own file
|
||||||
|
type Repost struct {
|
||||||
|
Type RepostType
|
||||||
|
|
||||||
|
Track *Track // type == track-report
|
||||||
|
Playlist *Playlist // type == playlist-repost
|
||||||
|
}
|
||||||
|
|
||||||
|
func (r *Repost) Fix() {
|
||||||
|
switch r.Type {
|
||||||
|
case TrackRepost:
|
||||||
|
if r.Track != nil {
|
||||||
|
r.Track.Fix(false)
|
||||||
|
}
|
||||||
|
return
|
||||||
|
case PlaylistRepost:
|
||||||
|
if r.Playlist != nil {
|
||||||
|
r.Playlist.Fix(false) // err always nil if cached == false
|
||||||
|
}
|
||||||
|
return
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
func GetUser(permalink string) (User, error) {
|
func GetUser(permalink string) (User, error) {
|
||||||
usersCacheLock.RLock()
|
usersCacheLock.RLock()
|
||||||
if cell, ok := usersCache[permalink]; ok && cell.Expires.After(time.Now()) {
|
if cell, ok := usersCache[permalink]; ok && cell.Expires.After(time.Now()) {
|
||||||
@@ -169,3 +199,20 @@ func (u *User) GetAlbums(args string) (*Paginated[*Playlist], error) {
|
|||||||
|
|
||||||
return &p, nil
|
return &p, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (u *User) GetReposts(args string) (*Paginated[*Repost], error) {
|
||||||
|
p := Paginated[*Repost]{
|
||||||
|
Next: "https://" + api + "/stream/users/" + u.ID + "/reposts" + args,
|
||||||
|
}
|
||||||
|
|
||||||
|
err := p.Proceed()
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, r := range p.Collection {
|
||||||
|
r.Fix()
|
||||||
|
}
|
||||||
|
|
||||||
|
return &p, nil
|
||||||
|
}
|
||||||
|
|||||||
17
main.go
17
main.go
@@ -198,6 +198,23 @@ func main() {
|
|||||||
return templates.Base(user.Username, templates.UserAlbums(user, pl), templates.UserHeader(user)).Render(context.Background(), c)
|
return templates.Base(user.Username, templates.UserAlbums(user, pl), templates.UserHeader(user)).Render(context.Background(), c)
|
||||||
})
|
})
|
||||||
|
|
||||||
|
app.Get("/:user/reposts", func(c *fiber.Ctx) error {
|
||||||
|
user, err := sc.GetUser(c.Params("user"))
|
||||||
|
if err != nil {
|
||||||
|
log.Printf("error getting %s (reposts): %s\n", c.Params("user"), err)
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
p, err := user.GetReposts(c.Query("pagination", "?limit=20"))
|
||||||
|
if err != nil {
|
||||||
|
log.Printf("error getting %s reposts: %s\n", c.Params("user"), err)
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
c.Set("Content-Type", "text/html")
|
||||||
|
return templates.Base(user.Username, templates.UserReposts(user, p), templates.UserHeader(user)).Render(context.Background(), c)
|
||||||
|
})
|
||||||
|
|
||||||
app.Get("/:user/:track", func(c *fiber.Ctx) error {
|
app.Get("/:user/:track", func(c *fiber.Ctx) error {
|
||||||
track, err := sc.GetTrack(c.Params("user") + "/" + c.Params("track"))
|
track, err := sc.GetTrack(c.Params("user") + "/" + c.Params("track"))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
|||||||
@@ -15,24 +15,31 @@ templ PlaylistHeader(p sc.Playlist) {
|
|||||||
<link rel="icon" type="image/x-icon" href={ p.Artwork }/>
|
<link rel="icon" type="image/x-icon" href={ p.Artwork }/>
|
||||||
}
|
}
|
||||||
|
|
||||||
|
templ PlaylistItem(playlist *sc.Playlist) {
|
||||||
|
<a class="listing" href={ templ.URL("/" + playlist.Author.Permalink + "/sets/" + playlist.Permalink) }>
|
||||||
|
if playlist.Artwork != "" {
|
||||||
|
<img src={ playlist.Artwork }/>
|
||||||
|
} else {
|
||||||
|
<img src="/placeholder.jpg"/>
|
||||||
|
}
|
||||||
|
<div class="meta">
|
||||||
|
<h3>{ playlist.Title }</h3>
|
||||||
|
<span>{ playlist.Author.Username }</span>
|
||||||
|
<p>{ strconv.FormatInt(playlist.TrackCount, 10) } tracks</p>
|
||||||
|
</div>
|
||||||
|
</a>
|
||||||
|
}
|
||||||
|
|
||||||
templ Playlist(p sc.Playlist) {
|
templ Playlist(p sc.Playlist) {
|
||||||
if p.Artwork != "" {
|
if p.Artwork != "" {
|
||||||
<img src={ p.Artwork } width="300px"/>
|
<img src={ p.Artwork } width="300px"/>
|
||||||
}
|
}
|
||||||
<h1>{ p.Title }</h1>
|
<h1>{ p.Title }</h1>
|
||||||
<a class="listing" href={ templ.URL("/" + p.Author.Permalink) }>
|
@UserItem(&p.Author)
|
||||||
<img src={ p.Author.Avatar }/>
|
|
||||||
<div class="meta">
|
|
||||||
<h3>{ p.Author.Username }</h3>
|
|
||||||
if p.Author.FullName != "" {
|
|
||||||
<span>{ p.Author.FullName }</span>
|
|
||||||
}
|
|
||||||
</div>
|
|
||||||
</a>
|
|
||||||
<div class="btns">
|
<div class="btns">
|
||||||
<a class="btn" href={ templ.URL("https://soundcloud.com/" + p.Author.Permalink + "/sets/" + p.Permalink) }>view on soundcloud</a>
|
<a class="btn" href={ templ.URL("https://soundcloud.com/" + p.Author.Permalink + "/sets/" + p.Permalink) }>view on soundcloud</a>
|
||||||
</div>
|
</div>
|
||||||
<br>
|
<br/>
|
||||||
if p.Description != "" {
|
if p.Description != "" {
|
||||||
<details>
|
<details>
|
||||||
<summary>Toggle description</summary>
|
<summary>Toggle description</summary>
|
||||||
@@ -44,19 +51,7 @@ templ Playlist(p sc.Playlist) {
|
|||||||
<br/>
|
<br/>
|
||||||
<div>
|
<div>
|
||||||
for _, track := range p.Tracks {
|
for _, track := range p.Tracks {
|
||||||
if track.Title != "" {
|
@TrackItem(track)
|
||||||
<a class="listing" href={ templ.URL("/" + track.Author.Permalink + "/" + track.Permalink) }>
|
|
||||||
if track.Artwork != "" {
|
|
||||||
<img src={ track.Artwork }/>
|
|
||||||
} else {
|
|
||||||
<img src="/placeholder.jpg"/>
|
|
||||||
}
|
|
||||||
<div class="meta">
|
|
||||||
<h3>{ track.Title }</h3>
|
|
||||||
<span>{ track.Author.Username }</span>
|
|
||||||
</div>
|
|
||||||
</a>
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
</div>
|
</div>
|
||||||
if len(p.MissingTracks) != 0 {
|
if len(p.MissingTracks) != 0 {
|
||||||
@@ -83,17 +78,7 @@ templ SearchPlaylists(p *sc.Paginated[*sc.Playlist]) {
|
|||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
for _, playlist := range p.Collection {
|
for _, playlist := range p.Collection {
|
||||||
<a class="listing" href={ templ.URL("/" + playlist.Author.Permalink + "/sets/" + playlist.Permalink) }>
|
@PlaylistItem(playlist)
|
||||||
if playlist.Artwork != "" {
|
|
||||||
<img src={ playlist.Artwork }/>
|
|
||||||
} else {
|
|
||||||
<img src="/placeholder.jpg"/>
|
|
||||||
}
|
|
||||||
<div class="meta">
|
|
||||||
<h3>{ playlist.Title }</h3>
|
|
||||||
<span>{ playlist.Author.Username }</span>
|
|
||||||
</div>
|
|
||||||
</a>
|
|
||||||
}
|
}
|
||||||
if p.Next != "" && len(p.Collection) != int(p.Total) {
|
if p.Next != "" && len(p.Collection) != int(p.Total) {
|
||||||
<a class="btn" href={ templ.URL("?type=playlists&pagination=" + url.QueryEscape(strings.Split(p.Next, "/playlists")[1])) } rel="noreferrer">more playlists</a>
|
<a class="btn" href={ templ.URL("?type=playlists&pagination=" + url.QueryEscape(strings.Split(p.Next, "/playlists")[1])) } rel="noreferrer">more playlists</a>
|
||||||
|
|||||||
@@ -25,6 +25,22 @@ templ TrackPlayer() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
templ TrackItem(track *sc.Track) {
|
||||||
|
if track.Title != "" {
|
||||||
|
<a class="listing" href={ templ.URL("/" + track.Author.Permalink + "/" + track.Permalink) }>
|
||||||
|
if track.Artwork != "" {
|
||||||
|
<img src={ track.Artwork }/>
|
||||||
|
} else {
|
||||||
|
<img src="/placeholder.jpg"/>
|
||||||
|
}
|
||||||
|
<div class="meta">
|
||||||
|
<h3>{ track.Title }</h3>
|
||||||
|
<span>{ track.Author.Username }</span>
|
||||||
|
</div>
|
||||||
|
</a>
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
templ Track(t sc.Track, stream string) {
|
templ Track(t sc.Track, stream string) {
|
||||||
if t.Artwork != "" {
|
if t.Artwork != "" {
|
||||||
<img src={ t.Artwork } width="300px"/>
|
<img src={ t.Artwork } width="300px"/>
|
||||||
@@ -42,19 +58,11 @@ templ Track(t sc.Track, stream string) {
|
|||||||
<br/>
|
<br/>
|
||||||
<br/>
|
<br/>
|
||||||
}
|
}
|
||||||
<a class="listing" href={ templ.URL("/" + t.Author.Permalink) }>
|
@UserItem(&t.Author)
|
||||||
<img src={ t.Author.Avatar }/>
|
|
||||||
<div class="meta">
|
|
||||||
<h3>{ t.Author.Username }</h3>
|
|
||||||
if t.Author.FullName != "" {
|
|
||||||
<span>{ t.Author.FullName }</span>
|
|
||||||
}
|
|
||||||
</div>
|
|
||||||
</a>
|
|
||||||
<div class="btns">
|
<div class="btns">
|
||||||
<a class="btn" href={ templ.URL("https://soundcloud.com/" + t.Author.Permalink + "/" + t.Permalink) }>view on soundcloud</a>
|
<a class="btn" href={ templ.URL("https://soundcloud.com/" + t.Author.Permalink + "/" + t.Permalink) }>view on soundcloud</a>
|
||||||
</div>
|
</div>
|
||||||
<br>
|
<br/>
|
||||||
if t.Description != "" {
|
if t.Description != "" {
|
||||||
<details>
|
<details>
|
||||||
<summary>Toggle description</summary>
|
<summary>Toggle description</summary>
|
||||||
@@ -95,15 +103,7 @@ templ TrackEmbed(t sc.Track, stream string) {
|
|||||||
<br/>
|
<br/>
|
||||||
JavaScript is disabled! Audio playback may not work without it enabled.
|
JavaScript is disabled! Audio playback may not work without it enabled.
|
||||||
</noscript>
|
</noscript>
|
||||||
<a class="listing" href={ templ.URL("/" + t.Author.Permalink) }>
|
@UserItem(&t.Author)
|
||||||
<img src={ t.Author.Avatar }/>
|
|
||||||
<div class="meta">
|
|
||||||
<h3>{ t.Author.Username }</h3>
|
|
||||||
if t.Author.FullName != "" {
|
|
||||||
<span>{ t.Author.FullName }</span>
|
|
||||||
}
|
|
||||||
</div>
|
|
||||||
</a>
|
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
}
|
}
|
||||||
@@ -116,17 +116,7 @@ templ SearchTracks(p *sc.Paginated[*sc.Track]) {
|
|||||||
<p>no more results</p>
|
<p>no more results</p>
|
||||||
} else {
|
} else {
|
||||||
for _, track := range p.Collection {
|
for _, track := range p.Collection {
|
||||||
<a class="listing" href={ templ.URL("/" + track.Author.Permalink + "/" + track.Permalink) }>
|
@TrackItem(track)
|
||||||
if track.Artwork != "" {
|
|
||||||
<img src={ track.Artwork }/>
|
|
||||||
} else {
|
|
||||||
<img src="/placeholder.jpg"/>
|
|
||||||
}
|
|
||||||
<div class="meta">
|
|
||||||
<h3>{ track.Title }</h3>
|
|
||||||
<span>{ track.Author.Username }</span>
|
|
||||||
</div>
|
|
||||||
</a>
|
|
||||||
}
|
}
|
||||||
if p.Next != "" && len(p.Collection) != int(p.Total) {
|
if p.Next != "" && len(p.Collection) != int(p.Total) {
|
||||||
<a class="btn" href={ templ.URL("?type=tracks&pagination=" + url.QueryEscape(strings.Split(p.Next, "/tracks")[1])) } rel="noreferrer">more tracks</a>
|
<a class="btn" href={ templ.URL("?type=tracks&pagination=" + url.QueryEscape(strings.Split(p.Next, "/tracks")[1])) } rel="noreferrer">more tracks</a>
|
||||||
|
|||||||
@@ -15,6 +15,22 @@ templ UserHeader(u sc.User) {
|
|||||||
<link rel="icon" type="image/x-icon" href={ u.Avatar }/>
|
<link rel="icon" type="image/x-icon" href={ u.Avatar }/>
|
||||||
}
|
}
|
||||||
|
|
||||||
|
templ UserItem(user *sc.User) {
|
||||||
|
<a class="listing" href={ templ.URL("/" + user.Permalink) }>
|
||||||
|
if user.Avatar != "" {
|
||||||
|
<img src={ user.Avatar }/>
|
||||||
|
} else {
|
||||||
|
<img src="/placeholder.jpg"/>
|
||||||
|
}
|
||||||
|
<div class="meta">
|
||||||
|
<h3>{ user.Username }</h3>
|
||||||
|
if user.FullName != "" {
|
||||||
|
<span>{ user.FullName }</span>
|
||||||
|
}
|
||||||
|
</div>
|
||||||
|
</a>
|
||||||
|
}
|
||||||
|
|
||||||
templ UserBase(u sc.User) {
|
templ UserBase(u sc.User) {
|
||||||
<div>
|
<div>
|
||||||
if u.Avatar != "" {
|
if u.Avatar != "" {
|
||||||
@@ -52,22 +68,14 @@ templ User(u sc.User, p *sc.Paginated[*sc.Track]) {
|
|||||||
<a class="btn active">tracks</a>
|
<a class="btn active">tracks</a>
|
||||||
<a class="btn" href={ templ.URL("/" + u.Permalink + "/sets") }>playlists</a>
|
<a class="btn" href={ templ.URL("/" + u.Permalink + "/sets") }>playlists</a>
|
||||||
<a class="btn" href={ templ.URL("/" + u.Permalink + "/albums") }>albums</a>
|
<a class="btn" href={ templ.URL("/" + u.Permalink + "/albums") }>albums</a>
|
||||||
|
<a class="btn" href={ templ.URL("/" + u.Permalink + "/reposts") }>reposts</a>
|
||||||
<a class="btn" href={ templ.URL("https://soundcloud.com/" + u.Permalink) }>view on soundcloud</a>
|
<a class="btn" href={ templ.URL("https://soundcloud.com/" + u.Permalink) }>view on soundcloud</a>
|
||||||
</div>
|
</div>
|
||||||
<br/>
|
<br/>
|
||||||
if len(p.Collection) != 0 {
|
if len(p.Collection) != 0 {
|
||||||
<div>
|
<div>
|
||||||
for _, track := range p.Collection {
|
for _, track := range p.Collection {
|
||||||
<a class="listing" href={ templ.URL("/" + track.Author.Permalink + "/" + track.Permalink) }>
|
@TrackItem(track)
|
||||||
if track.Artwork != "" {
|
|
||||||
<img src={ track.Artwork }/>
|
|
||||||
} else {
|
|
||||||
<img src="/placeholder.jpg"/>
|
|
||||||
}
|
|
||||||
<div class="meta">
|
|
||||||
<h3>{ track.Title }</h3>
|
|
||||||
</div>
|
|
||||||
</a>
|
|
||||||
}
|
}
|
||||||
</div>
|
</div>
|
||||||
if p.Next != "" && len(p.Collection) != int(u.Tracks) {
|
if p.Next != "" && len(p.Collection) != int(u.Tracks) {
|
||||||
@@ -84,22 +92,14 @@ templ UserPlaylists(u sc.User, p *sc.Paginated[*sc.Playlist]) {
|
|||||||
<a class="btn" href={ templ.URL("/" + u.Permalink) }>tracks</a>
|
<a class="btn" href={ templ.URL("/" + u.Permalink) }>tracks</a>
|
||||||
<a class="btn active">playlists</a>
|
<a class="btn active">playlists</a>
|
||||||
<a class="btn" href={ templ.URL("/" + u.Permalink + "/albums") }>albums</a>
|
<a class="btn" href={ templ.URL("/" + u.Permalink + "/albums") }>albums</a>
|
||||||
|
<a class="btn" href={ templ.URL("/" + u.Permalink + "/reposts") }>reposts</a>
|
||||||
<a class="btn" href={ templ.URL("https://soundcloud.com/" + u.Permalink) }>view on soundcloud</a>
|
<a class="btn" href={ templ.URL("https://soundcloud.com/" + u.Permalink) }>view on soundcloud</a>
|
||||||
</div>
|
</div>
|
||||||
<br/>
|
<br/>
|
||||||
if len(p.Collection) != 0 {
|
if len(p.Collection) != 0 {
|
||||||
<div>
|
<div>
|
||||||
for _, playlist := range p.Collection {
|
for _, playlist := range p.Collection {
|
||||||
<a class="listing" href={ templ.URL("/" + playlist.Author.Permalink + "/sets/" + playlist.Permalink) }>
|
@PlaylistItem(playlist)
|
||||||
if playlist.Artwork != "" {
|
|
||||||
<img src={ playlist.Artwork }/>
|
|
||||||
} else {
|
|
||||||
<img src="/placeholder.jpg"/>
|
|
||||||
}
|
|
||||||
<div class="meta">
|
|
||||||
<h3>{ playlist.Title }</h3>
|
|
||||||
</div>
|
|
||||||
</a>
|
|
||||||
}
|
}
|
||||||
</div>
|
</div>
|
||||||
if p.Next != "" && len(p.Collection) != int(p.Total) {
|
if p.Next != "" && len(p.Collection) != int(p.Total) {
|
||||||
@@ -116,22 +116,14 @@ templ UserAlbums(u sc.User, p *sc.Paginated[*sc.Playlist]) {
|
|||||||
<a class="btn" href={ templ.URL("/" + u.Permalink) }>tracks</a>
|
<a class="btn" href={ templ.URL("/" + u.Permalink) }>tracks</a>
|
||||||
<a class="btn" href={ templ.URL("/" + u.Permalink + "/sets") }>playlists</a>
|
<a class="btn" href={ templ.URL("/" + u.Permalink + "/sets") }>playlists</a>
|
||||||
<a class="btn active">albums</a>
|
<a class="btn active">albums</a>
|
||||||
|
<a class="btn" href={ templ.URL("/" + u.Permalink + "/reposts") }>reposts</a>
|
||||||
<a class="btn" href={ templ.URL("https://soundcloud.com/" + u.Permalink) }>view on soundcloud</a>
|
<a class="btn" href={ templ.URL("https://soundcloud.com/" + u.Permalink) }>view on soundcloud</a>
|
||||||
</div>
|
</div>
|
||||||
<br/>
|
<br/>
|
||||||
if len(p.Collection) != 0 {
|
if len(p.Collection) != 0 {
|
||||||
<div>
|
<div>
|
||||||
for _, playlist := range p.Collection {
|
for _, playlist := range p.Collection {
|
||||||
<a class="listing" href={ templ.URL("/" + playlist.Author.Permalink + "/sets/" + playlist.Permalink) }>
|
@PlaylistItem(playlist)
|
||||||
if playlist.Artwork != "" {
|
|
||||||
<img src={ playlist.Artwork }/>
|
|
||||||
} else {
|
|
||||||
<img src="/placeholder.jpg"/>
|
|
||||||
}
|
|
||||||
<div class="meta">
|
|
||||||
<h3>{ playlist.Title }</h3>
|
|
||||||
</div>
|
|
||||||
</a>
|
|
||||||
}
|
}
|
||||||
</div>
|
</div>
|
||||||
if p.Next != "" && len(p.Collection) != int(p.Total) {
|
if p.Next != "" && len(p.Collection) != int(p.Total) {
|
||||||
@@ -142,6 +134,34 @@ templ UserAlbums(u sc.User, p *sc.Paginated[*sc.Playlist]) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
templ UserReposts(u sc.User, p *sc.Paginated[*sc.Repost]) {
|
||||||
|
@UserBase(u)
|
||||||
|
<div class="btns">
|
||||||
|
<a class="btn" href={ templ.URL("/" + u.Permalink) }>tracks</a>
|
||||||
|
<a class="btn" href={ templ.URL("/" + u.Permalink + "/sets") }>playlists</a>
|
||||||
|
<a class="btn" href={ templ.URL("/" + u.Permalink + "/albums") }>albums</a>
|
||||||
|
<a class="btn active">reposts</a>
|
||||||
|
<a class="btn" href={ templ.URL("https://soundcloud.com/" + u.Permalink) }>view on soundcloud</a>
|
||||||
|
</div>
|
||||||
|
<br/>
|
||||||
|
if len(p.Collection) != 0 {
|
||||||
|
<div>
|
||||||
|
for _, repost := range p.Collection {
|
||||||
|
if repost.Type == sc.TrackRepost && repost.Track != nil {
|
||||||
|
@TrackItem(repost.Track)
|
||||||
|
} else if repost.Type == sc.PlaylistRepost && repost.Playlist != nil {
|
||||||
|
@PlaylistItem(repost.Playlist)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
</div>
|
||||||
|
if p.Next != "" && len(p.Collection) != int(p.Total) {
|
||||||
|
<a class="btn" href={ templ.URL("?pagination=" + url.QueryEscape(strings.Split(p.Next, "/reposts")[1])) } rel="noreferrer">more reposts</a>
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
<span>no more reposts</span>
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
templ SearchUsers(p *sc.Paginated[*sc.User]) {
|
templ SearchUsers(p *sc.Paginated[*sc.User]) {
|
||||||
<span>Found { strconv.FormatInt(p.Total, 10) } users</span>
|
<span>Found { strconv.FormatInt(p.Total, 10) } users</span>
|
||||||
<br/>
|
<br/>
|
||||||
@@ -152,19 +172,7 @@ templ SearchUsers(p *sc.Paginated[*sc.User]) {
|
|||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
for _, user := range p.Collection {
|
for _, user := range p.Collection {
|
||||||
<a class="listing" href={ templ.URL("/" + user.Permalink) }>
|
@UserItem(user)
|
||||||
if user.Avatar != "" {
|
|
||||||
<img src={ user.Avatar }/>
|
|
||||||
} else {
|
|
||||||
<img src="/placeholder.jpg"/>
|
|
||||||
}
|
|
||||||
<div class="meta">
|
|
||||||
<h3>{ user.Username }</h3>
|
|
||||||
if user.FullName != "" {
|
|
||||||
<span>{ user.FullName }</span>
|
|
||||||
}
|
|
||||||
</div>
|
|
||||||
</a>
|
|
||||||
}
|
}
|
||||||
if p.Next != "" && len(p.Collection) != int(p.Total) {
|
if p.Next != "" && len(p.Collection) != int(p.Total) {
|
||||||
<a class="btn" href={ templ.URL("?type=users&pagination=" + url.QueryEscape(strings.Split(p.Next, "/users")[1])) } rel="noreferrer">more users</a>
|
<a class="btn" href={ templ.URL("?type=users&pagination=" + url.QueryEscape(strings.Split(p.Next, "/users")[1])) } rel="noreferrer">more users</a>
|
||||||
|
|||||||
Reference in New Issue
Block a user